Messages Since

Query · messagesSince

messagesSince(afterSequence: Int!, conversationId: ID!, first: Int! = 50): MessagePage!

Lấy các tin nhắn có sequence lớn hơn mốc client đã giữ, theo thứ tự tăng dần. Dùng sau khi WebSocket kết nối lại hoặc khi nghi ngờ bỏ lỡ sự kiện: subscription chỉ thông báo theo thời gian thực, còn query này đọc dữ liệu đã lưu. Bắt đầu bằng afterSequence: 0 để lấy từ đầu conversation. Query không tự cập nhật mốc đã đọc.

Gửi query qua HTTP POST /graphql với Authorization: Bearer <accessToken>. Người gọi phải là thành viên conversation. Tin đã xóa mềm vẫn nằm trong luồng sequence nhưng có content: null và không có tệp đính kèm.

Input

Đối sốKiểu GraphQLBắt buộcQuy tắc và ý nghĩa
afterSequenceInt!CóSequence cuối cùng client đã giữ; số nguyên không âm, 0 hợp lệ. Chỉ trả tin có sequence lớn hơn mốc này. Không có giá trị mặc định.
conversationIdID!CóUUID của conversation; không có giá trị mặc định.
firstInt!Không nếu bỏ quaSố tin tối đa trong một trang, từ 1 đến 100; mặc định 50. Không nhận null.

Output

Trả về MessagePage!, không null. nodes tăng dần theo sequence. Nếu hasNextPage là true, gọi tiếp với afterSequence bằng sequence của tin cuối trong nodes; endCursor chỉ biểu thị mốc cuối trang, không phải đối số của query này. Trang rỗng có endCursor: null.

MessagePage

TrườngKiểu GraphQLÝ nghĩa
nodes[MessageView!]!Tin nhắn mới hơn mốc đã cho; danh sách và phần tử không null. Xem MessageView.
endCursorStringCursor mã hóa conversation và sequence mới nhất trong trang, hoặc null nếu rỗng.
hasNextPageBoolean!true nếu còn tin mới hơn sau trang này.

MessageView

TrườngKiểu GraphQLÝ nghĩa
idID!ID tin nhắn trên server.
clientMessageIdString!ID client gửi, dùng đối chiếu retry và tin nhắn lạc quan.
conversationIdID!Conversation chứa tin nhắn.
senderIdID!Người gửi.
sequenceInt!Thứ tự tăng trong conversation.
typeMessageType!TEXT cho tin do người dùng gửi; schema còn có SYSTEM.
contentStringNội dung hoặc null khi đã xóa mềm; có thể rỗng khi chỉ gửi tệp.
replyToMessageIdIDID tin được trả lời hoặc null.
replyToMessageSummaryTóm tắt tin được trả lời hoặc null; xem MessageSummary.
createdAtDateTime!Thời điểm tạo.
updatedAtDateTime!Thời điểm cập nhật.
deletedAtDateTimeThời điểm xóa mềm hoặc null.
attachments[MessageAttachmentView!]!Tệp còn truy cập được; rỗng khi tin đã xóa. Xem MessageAttachmentView.
reactions[ReactionSummary!]!Phản ứng nhóm theo emoji. Xem ReactionSummary.

MessageSummary

TrườngKiểu GraphQLÝ nghĩa
idID!ID tin được trả lời.
senderIdID!Người gửi tin đó.
contentStringNội dung hoặc null nếu đã xóa.
deletedAtDateTimeThời điểm xóa mềm hoặc null.

MessageAttachmentView

TrườngKiểu GraphQLÝ nghĩa
idID!ID tệp đính kèm.
fileNameString!Tên tệp hiển thị.
contentTypeString!MIME type.
sizeInt!Kích thước byte do client báo khi gửi.

ReactionSummary

TrườngKiểu GraphQLÝ nghĩa
emojiString!Emoji phản ứng.
userIds[ID!]!ID những người đã dùng emoji này; danh sách và phần tử không null.

Ví dụ

query MessagesSince($conversationId: ID!, $afterSequence: Int!, $first: Int!) {
  messagesSince(conversationId: $conversationId, afterSequence: $afterSequence, first: $first) {
    nodes {
      id
      clientMessageId
      conversationId
      senderId
      sequence
      type
      content
      replyToMessageId
      replyTo { id senderId content deletedAt }
      createdAt
      updatedAt
      deletedAt
      attachments { id fileName contentType size }
      reactions { emoji userIds }
    }
    endCursor
    hasNextPage
  }
}

Biến:

{
  "conversationId": "33333333-3333-4333-8333-333333333333",
  "afterSequence": 3,
  "first": 1
}

Phản hồi minh họa:

{
  "data": {
    "messagesSince": {
      "nodes": [
        {
          "id": "44444444-4444-4444-8444-444444444444",
          "clientMessageId": "send-004",
          "conversationId": "33333333-3333-4333-8333-333333333333",
          "senderId": "11111111-1111-4111-8111-111111111111",
          "sequence": 4,
          "type": "TEXT",
          "content": "Chào bạn",
          "replyToMessageId": null,
          "replyTo": null,
          "createdAt": "2026-09-26T09:00:00.000Z",
          "updatedAt": "2026-09-26T09:00:00.000Z",
          "deletedAt": null,
          "attachments": [],
          "reactions": []
        }
      ],
      "endCursor": "WyIzMzMzMzMzMy0zMzMzLTQzMzMtODMzMy0zMzMzMzMzMzMzMzMiLCI0Il0",
      "hasNextPage": true
    }
  }
}

Nếu còn trang, gọi tiếp với afterSequence: 4. Thiếu hoặc sai access token trả UNAUTHENTICATED; ID conversation sai định dạng, afterSequence âm hoặc first ngoài 1–100 trả BAD_USER_INPUT. Không phải thành viên nhận FORBIDDEN.

Chữ ký operation được tạo từ GraphQL schema.