Query comments

Fetch comments for any record, discussion, or status update with the commentList query — scoped by category, paginated, and ordered.


Use the commentList query to read comments from any surface in Blue. There is one comment store across the product, so a single query serves all three targets: pass a category (DISCUSSION, STATUS_UPDATE, or TODO) plus the categoryId of the thing you’re reading. The result is a CommentList with the page of comments, pagination metadata, and a totalCount.

commentList is the canonical way to fetch comments. The older Discussion.comments, StatusUpdate.comments, and Todo.comments fields are deprecated in favor of it — see Comments overview for the comment model and the category/categoryId targeting convention.

Request

Fetch the top-level comments on a record. category is TODO and categoryId is the record (Todo) ID.

query RecordComments {
  commentList(category: TODO, categoryId: "todo_123") {
    comments {
      id
      text
      createdAt
      user {
        id
        fullName
      }
    }
    totalCount
  }
}

The same query shape reads a discussion (category: DISCUSSION, categoryId = the discussion ID) or a status update (category: STATUS_UPDATE, categoryId = the status-update ID). Only category and categoryId change.

Top-level comments only

commentList returns only the root comments of a thread — those with parentId = null. Threaded replies are not included in the page. Fetch a comment’s replies through its replies field (and replyCount); see Comments overview.

Parameters

Arguments

ArgumentTypeRequiredDescription
categoryCommentCategory!YesWhich kind of target you’re reading. Pairs with categoryId.
categoryIdString!YesThe ID of the target: a discussion ID, a status-update ID, or a record (Todo) ID, per category.
firstIntNoPage size — how many comments to return. Omit to return all matching comments (subject to skip).
skipIntNoNumber of comments to skip before the page, for offset pagination. Defaults to 0.
afterStringNoCursor: return comments whose id is greater than or equal to this value. Use a comment id.
orderByDiscussionOrderByInputNoSort order. Defaults to createdAt_ASC (oldest first).
beforeStringNoAccepted by the schema but not applied by this query. Paginate with first + skip (or after).
lastIntNoAccepted by the schema but not applied by this query. Use first for the page size.
before and last are no-ops here

The schema accepts before and last, but commentList ignores them. Page with first + skip for offset pagination, or after for an id-cursor scan. Sending before/last has no effect on the result.

CommentCategory

ValuecategoryId is the ID ofRead instead via
DISCUSSIONA discussion threadQuery discussions
STATUS_UPDATEA status updateThe status update’s ID
TODOA record (Todo)List records

DiscussionOrderByInput

orderBy takes a single DiscussionOrderByInput value (the type is shared with discussionList). For comments the meaningful sorts are by timestamp:

ValueSorts comments by
createdAt_ASC / createdAt_DESCCreation time. createdAt_ASC is default.
updatedAt_ASC / updatedAt_DESCLast-edited time.
id_ASC / id_DESCComment ID.

Response

{
  "data": {
    "commentList": {
      "comments": [
        {
          "id": "clm4n8qwx000008l0g4oxdqn7",
          "text": "Kicking off the launch checklist — see the linked doc.",
          "createdAt": "2026-05-20T09:14:00.000Z",
          "user": {
            "id": "clm4n8qwx000108l0haz1f2pe",
            "fullName": "Ada Lovelace"
          }
        },
        {
          "id": "clm4n8qwx000208l0bk7c9xqz",
          "text": "Pricing copy is approved.",
          "createdAt": "2026-05-21T16:02:00.000Z",
          "user": {
            "id": "clm4n8qwx000308l0e1g5m4ab",
            "fullName": "Grace Hopper"
          }
        }
      ],
      "totalCount": 2
    }
  }
}

CommentList

FieldTypeDescription
comments[Comment!]!The top-level comments on this page, in orderBy order.
pageInfoPageInfo!Pagination metadata for the page (below).
totalCountInt!Total top-level comments on the target, across all pages.

PageInfo

FieldTypeDescription
totalItemsIntTotal matching comments, across all pages (mirrors totalCount).
totalPagesIntTotal pages at the current first.
pageIntCurrent page, derived from skip and first.
perPageIntPage size in effect (the resolved first).
hasNextPageBoolean!Whether a next page exists.
hasPreviousPageBoolean!Whether a previous page exists.
startCursorStringDeprecated. Paginate with first/skip (or after), not these cursors.
endCursorStringDeprecated. See startCursor.

Comment

The fields you’ll select most often. The Comment type exposes more — these are the common ones; the full set is documented in Comments overview.

FieldTypeDescription
idID!Unique identifier.
uidString!Short, human-facing identifier.
htmlString!Comment body as HTML.
textString!Comment body as plain text.
categoryCommentCategory!The target kind this comment belongs to.
createdAtDateTime!Creation timestamp.
updatedAtDateTime!Last-edited timestamp.
deletedAtDateTimeSet when the comment was soft-deleted; the body is blanked but the row remains.
deletedByUserWho soft-deleted the comment. Select fullName/email, not name.
userUser!The author. Select fullName/email, not name.
parentIdStringThe parent comment’s ID when this is a reply. Always null for items returned here.
parentCommentThe parent comment, when this is a reply.
replies[Comment!]!Threaded replies to this comment.
replyCountInt!Number of replies.
isReadBooleanRead state for the current user.
isSeenBooleanSeen state for the current user.
reactions[ReactionGroup!]!Emoji reactions on the comment. See Reactions.
discussionDiscussionThe parent discussion, when category is DISCUSSION.
statusUpdateStatusUpdateThe parent status update, when category is STATUS_UPDATE.
todoTodoThe parent record, when category is TODO.

Full example

Read the second page of a discussion’s comments (10 per page, newest first), with reply counts and reactions.

query DiscussionComments {
  commentList(
    category: DISCUSSION
    categoryId: "discussion_123"
    first: 10
    skip: 10
    orderBy: createdAt_DESC
  ) {
    comments {
      id
      uid
      html
      text
      createdAt
      updatedAt
      replyCount
      isRead
      user {
        id
        fullName
        email
      }
      reactions {
        emoji
        count
        reactedByMe
      }
    }
    pageInfo {
      totalItems
      totalPages
      page
      perPage
      hasNextPage
      hasPreviousPage
    }
    totalCount
  }
}

Errors

This query degrades gracefully: a categoryId that doesn’t exist (or points at a target you can’t see) yields an empty comments list and a totalCount of 0, rather than an error. Errors are reserved for authentication.

CodeWhen
UNAUTHENTICATEDThe request carries no valid credentials.

Permissions

Any authenticated caller can run commentList. Visibility is then scoped to the caller:

  • A role configured with show-only-mentioned-comments sees a filtered subset — only comments the user authored or in which the user is mentioned. totalCount reflects that filtered set, not the thread’s full comment count.
  • Comments on targets the caller can’t access return nothing rather than erroring.