> ## Documentation Index
> Fetch the complete documentation index at: https://social-b97141fb-feat-user-history-moderation-detail.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# Text Comment

> Create text comments and replies on posts, stories, or custom content.

Create a text comment by passing a reference target and text body to the comment repository. To create a reply, pass the parent comment ID with the same reference target.

## Parameters

| Parameter | Required | Platforms | Description |
| - | - | - | - |
| `referenceId` | Yes | All | ID of the post, story, or custom content item being commented on |
| `referenceType` | Yes | All | Use `post`, `story`, or `content` |
| `text` | Yes | All | Text body of the comment |
| `parentId` | No | All | Existing comment ID when creating a reply |
| `metadata` | No | All | Custom metadata attached to the comment |
| `mentionees` / mention builder | No | All | User mention payloads |
| `links` | No | TypeScript, iOS, Android | Link metadata; not exposed on the Flutter comment builder |

<Info>
  The current Flutter public comment creation builder exposes `metadata(...)` and `mentionUsers(...)`, but it does not expose a `links(...)` method.
</Info>

## Create a Text Comment

Create a top-level text comment with the reference target and text body.

<Note>
  Comment creation is local-first on TypeScript, iOS, Android, and React Native: the SDK persists a local comment before the server confirms it. See [Local-First Comment Creation](#local-first-comment-creation) for the per-platform sync states and failure handling.
</Note>

<CodeGroup>
  ```typescript TypeScript theme={null}
  import { CommentRepository } from "@amityco/ts-sdk";

  const { data: comment } = await CommentRepository.createComment({
    referenceId: postId,
    referenceType: "post",
    data: {
      text: "Hello world!",
    },
  });

  renderResults(comment);
  ```

  ```swift iOS theme={null}
  let options = AmityCommentCreateOptions(
      referenceId: "post-id",
      referenceType: .post,
      text: "Hello world!"
  )

  let comment = try await commentRepository.createComment(with: options)
  showSuccessMessage(comment.commentId)
  ```

  ```kotlin Android theme={null}
  AmitySocialClient.newCommentRepository()
      .createComment()
      .post(postId = postId)
      .with()
      .text(text = "Hello world!")
      .build()
      .send()
      .subscribe(
          { comment -> showSuccessMessage(comment.getCommentId()) },
          { error -> handleGeneralError(error) }
      )
  ```

  ```dart Flutter theme={null}
  final comment = await AmitySocialClient.newCommentRepository()
      .createComment()
      .post(postId)
      .create()
      .text('Hello world!')
      .send();

  final commentId = comment.commentId;
  ```
</CodeGroup>

## Reply to a Comment

Replies use the same creation API with `parentId` set to the comment being replied to.

<CodeGroup>
  ```typescript TypeScript theme={null}
  import { CommentRepository } from "@amityco/ts-sdk";

  const { data: reply } = await CommentRepository.createComment({
    referenceId: postId,
    referenceType: "post",
    parentId: commentId,
    data: {
      text: "Replying to this comment",
    },
  });

  renderResults(reply);
  ```

  ```swift iOS theme={null}
  let options = AmityCommentCreateOptions(
      referenceId: "post-id",
      referenceType: .post,
      text: "Replying to this comment",
      parentId: "parent-comment-id"
  )

  let reply = try await commentRepository.createComment(with: options)
  showSuccessMessage(reply.commentId)
  ```

  ```kotlin Android theme={null}
  AmitySocialClient.newCommentRepository()
      .createComment()
      .post(postId = postId)
      .parentId(parentId = commentId)
      .with()
      .text(text = "Replying to this comment")
      .build()
      .send()
      .subscribe(
          { reply -> showSuccessMessage(reply.getCommentId()) },
          { error -> handleGeneralError(error) }
      )
  ```

  ```dart Flutter theme={null}
  final reply = await AmitySocialClient.newCommentRepository()
      .createComment()
      .post(postId)
      .parentId(commentId)
      .create()
      .text('Replying to this comment')
      .send();

  final replyId = reply.commentId;
  ```
</CodeGroup>

## Add Structured Links

TypeScript, iOS, and Android accept a `links` payload when creating a comment, which stores the links found in the comment text alongside the comment.

Comments highlight link text; they do not render link preview cards. Build each link with `renderPreview: false` and leave the preview metadata fields unset — a comment never needs a preview metadata lookup.

Each link carries:

| Field | Required | Description |
| - | - | - |
| `url` | Yes | The link target. |
| `renderPreview` | Yes | Set `false` for comments. Comments never render preview cards, so this value does not affect how a comment link displays. |
| `index`, `length` | No | Position and length of the link text within the comment text. Include both whenever you send a `links` payload. |
| `domain`, `title`, `imageUrl` | No | Preview card metadata. Leave unset for comments. |

<Info>
  Sending `links` is optional. Clients detect URLs in the comment text and highlight them on their own, so a comment created without a `links` payload still renders highlighted links. When you do send the payload, include `index` and `length` for every link. On Android, `AmityLink` has no default arguments — pass `null` for every field you are not setting.
</Info>

<CodeGroup>
  ```typescript TypeScript theme={null}
  import { CommentRepository } from "@amityco/ts-sdk";

  const { data: comment } = await CommentRepository.createComment({
    referenceId: postId,
    referenceType: "post",
    data: {
      text: "Check this out https://www.amity.co",
    },
    links: [
      {
        index: 15,
        length: 20,
        url: "https://www.amity.co",
        renderPreview: false,
      },
    ],
  });

  renderResults(comment);
  ```

  ```swift iOS theme={null}
  let options = AmityCommentCreateOptions(
      referenceId: "post-id",
      referenceType: .post,
      text: "Check this out https://www.amity.co",
      links: [
          AmityLink(
              url: "https://www.amity.co",
              index: 15,
              length: 20,
              renderPreview: false
          )
      ]
  )

  let comment = try await commentRepository.createComment(with: options)
  showSuccessMessage(comment.commentId)
  ```

  ```kotlin Android theme={null}
  val links = listOf(
      AmityLink(
          index = 15,
          length = 20,
          url = "https://www.amity.co",
          renderPreview = false,
          domain = null,
          title = null,
          imageUrl = null
      )
  )

  AmitySocialClient.newCommentRepository()
      .createComment()
      .post(postId = postId)
      .with()
      .text(text = "Check this out https://www.amity.co")
      .links(links = links)
      .build()
      .send()
      .subscribe(
          { comment -> showSuccessMessage(comment.getCommentId()) },
          { error -> handleGeneralError(error) }
      )
  ```
</CodeGroup>

<Note>
  When editing a comment on iOS, `links` follows update semantics: pass `nil` to leave the existing links unchanged, or `[]` to remove them all. See [Edit Comment](../actions/edit-comment).
</Note>

## Local-First Comment Creation

On TypeScript, iOS, Android, and React Native, the SDK writes the comment to its local store and starts the server request immediately, so an active comment collection can render it before the round trip completes. Flutter waits for the server response instead.

The state is observable on every local-first platform, but the names and failure behavior differ:

| Platform | State and failure behavior |
| - | - |
| TypeScript | Read `comment.syncState`: `syncing` while the request is in flight, `synced` after server confirmation, or `error` when creation fails. The optimistic item remains in the collection on failure and carries a temporary local comment ID. |
| iOS | Observe `AmityComment.syncState`: `.syncing` becomes `.synced` after confirmation. A failed local comment becomes `.error` and is removed from its parent relationship, so it no longer appears among its parent's children. |
| Android | Read `comment.getState()`: `SYNCING` becomes `SYNCED` after confirmation. A failed local comment is marked `FAILED` in the local store. |
| Flutter | The current public comment-creation path waits for the server response before persisting the comment; it does not create the same local-first temporary comment. |
| React Native | Uses `@amityco/ts-sdk-react-native`, which shares the TypeScript implementation and behaves identically. |

Render local-first comments in a pending style, and handle each platform's failure state so a failed comment is not mistaken for a server-created one.

<Warning>
  On TypeScript and React Native, local-first creation requires the client cache. When the cache is disabled no local comment is created, and the call behaves like a plain server request.
</Warning>

The creation call also rejects when the server request fails; it does not only set the failure state. Catch the error from the creation call and watch sync state through the live collection or observable query. Handling only one of the two leaves either an unhandled rejection or a pending comment that never resolves.

## Notes

* Keep the same `referenceId` and `referenceType` as the thread you are replying in.
* Use query APIs or live collections to display creation and sync state in the UI.
* Validate your product's text limits and moderation rules before calling the SDK.
* Build mention payloads from the user IDs your mention picker returns.

## Related Topics

<CardGroup cols={2}>
  <Card title="Image Comment" icon="image" href="./image-comment">
    Create comments with uploaded image attachments.
  </Card>

  <Card title="Query Comments" icon="filter" href="../retrieval/query-comments">
    Query top-level comments and reply threads.
  </Card>
</CardGroup>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.