> ## Documentation Index
> Fetch the complete documentation index at: https://cometchat-22654f5b-docs-llms-scoped-indexes.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# AI Agents

> Integrate AI Agents into your React Native app using the CometChat SDK, including real-time event streaming and agentic message handling.

<Accordion title="AI Integration Quick Reference">
  | Field | Value |
  | - | - |
  | Package | `@cometchat/chat-sdk-react-native` |
  | Import | `import { CometChat } from "@cometchat/chat-sdk-react-native";` |
  | Key Classes | `AIAssistantMessage`, `AIToolResultMessage`, `AIToolArgumentMessage`, `AIAssistantBaseEvent`, `AIAssistantCardStartedEvent`, `AIAssistantCardReceivedEvent`, `AIAssistantCardEndedEvent`, `AIAssistantElement`, `MessageListener` |
  | Key Methods | `addAIAssistantListener()`, `removeAIAssistantListener()`, `addMessageListener()`, `removeMessageListener()` |
  | Listener Events | `onAIAssistantEventReceived` (streaming run events); `onAIAssistantMessageReceived`, `onAIToolResultReceived`, `onAIToolArgumentsReceived` (persisted messages) |
  | Primary output | Live run events arrive on `onAIAssistantEventReceived` as `AIAssistantBaseEvent` subclasses; once the run completes the persisted messages arrive on the `MessageListener` |
  | Prerequisites | SDK initialized via `CometChat.init()`, user logged in via `CometChat.login()`; an agent with the `@agentic` role configured in the [dashboard](https://app.cometchat.com/) |
  | Related | [AI Moderation](/sdk/react-native/ai-moderation), [Receive Messages](/sdk/react-native/receive-messages) |
  | Constraints | `AIAssistantCardEndedEvent` and `AIAssistantElement` ship only in newer SDK builds — they are absent from 4.0.21. Every `add*Listener()` needs a matching `remove*Listener()` with the same listener ID — unremoved listeners leak and fire after unmount. |
  | Full reference | [`AIAssistantMessage`](/sdk/reference/messages#aiassistantmessage) · [`AIToolResultMessage`](/sdk/reference/messages#aitoolresultmessage) · [`AIToolArgumentMessage`](/sdk/reference/messages#aitoolargumentmessage) · [`AIAssistantBaseEvent`](/sdk/reference/messages#aiassistantbaseevent) |
</Accordion>

AI Agents enable intelligent, automated interactions within your application. They process user messages, trigger tools, and respond with contextually relevant information. For a broader introduction, see the [AI Agents section](/ai-agents).

<Note>
  Agents only respond to text messages.
</Note>

## Agent Run Lifecycle and Message Flow

When a user sends a text message to an Agent:

1. The platform starts a run and streams real-time events via `AIAssistantListener`
2. After the run completes, persisted Agentic Messages arrive via `MessageListener`

### Real-time Events

Events are received via the **`onAIAssistantEventReceived`** method of the **`AIAssistantListener`** class as [`AIAssistantBaseEvent`](/sdk/reference/messages#aiassistantbaseevent) objects, in this general order:

Events arrive via `onAIAssistantEventReceived` in this order:

| Order | Event | Description |
| - | - | - |
| 1 | Run Start | A new run has begun |
| 2 | Tool Call Start | Agent decided to invoke a tool |
| 3 | Tool Call Arguments | Arguments being passed to the tool |
| 4 | Tool Call End | Tool execution completed |
| 5 | Tool Call Result | Tool's output is available |
| 6 | Card Start | Agent started generating a card |
| 7 | Card | Full card payload is available |
| 8 | Card End | Card generation is complete |
| 9 | Text Message Start | Agent started composing a reply |
| 10 | Text Message Content | Streaming content chunks (multiple) |
| 11 | Text Message End | Agent reply is complete |
| 12 | Run Finished | Run finalized; persisted messages follow |

<Note>
  `Run Start` and `Run Finished` are always emitted. Tool Call events only appear when tools are invoked — there can be multiple tool call cycles in a single run. Card events (`Card Start` → `Card` → `Card End`) only appear when the agent produces a card, and may repeat for each card. Text Message events are always emitted and carry the assistant's reply incrementally.
</Note>

### Event Object Properties

Every event is an `AIAssistantBaseEvent` with these common properties:

| Getter | Return Type | Description |
| - | - | - |
| `getType()` | `string` | Event type (e.g., `run_started`, `text_message_content`) |
| `getConversationId()` | `string` | The conversation this event belongs to |
| `getMessageId()` | `string` | The message ID associated with the event |
| `getParentMessageId()` | `string` | Parent message ID (for threaded messages) |
| `getRunId()` | `string` | The run ID for this agent execution |
| `getThreadId()` | `string` | The thread ID for this agent execution |
| `getTimestamp()` | `number` | Timestamp of the event |
| `getData()` | `object` | Full event data payload |

Some events carry additional data:

| Event | Extra Getter | Description |
| - | - | - |
| Text Message Content | `getDelta()` | The streaming text chunk for progressive rendering |
| Tool Call Arguments | `getToolCallId()`, `getDelta()` | Tool call ID and argument chunk |
| Tool Call Result | `getToolCallId()`, `getContent()`, `getRole()` | Tool call ID, result content, and role |
| Card Start | `getCardId()`, `getExecutionText()`, `getStreamMessageId()` | Card ID, a human-readable status string, and the stream message ID |
| Card | `getCardId()`, `getCard()`, `getStreamMessageId()` | Card ID, the raw card payload, and the stream message ID |
| Card End | `getCardId()`, `getStreamMessageId()` | Card ID and the stream message ID |

<Tabs>
  <Tab title="TypeScript">
    ```ts theme={null}
            const listnerId: string = "unique_listener_id";

            // Adding the AIAssistantListener
            CometChat.addAIAssistantListener(listnerId, {
                onAIAssistantEventReceived: (message: CometChat.AIAssistantBaseEvent) => {
                    console.log("AIAssistant event received successfully", message);
                }
            });

            // Removing the AIAssistantListener
            CometChat.removeAIAssistantListener(listnerId);
    ```
  </Tab>

  <Tab title="JavaScript">
    ```js theme={null}
            const listnerId = "unique_listener_id";

            // Adding the AIAssistantListener
            CometChat.addAIAssistantListener(listnerId, {
                onAIAssistantEventReceived: (message) => {
                    console.log("AIAssistant event received successfully", message);
                }
            });

            // Removing the AIAssistantListener
            CometChat.removeAIAssistantListener(listnerId);
    ```
  </Tab>
</Tabs>

<Warning>
  Always remove AI Assistant listeners when the component unmounts to prevent memory leaks.

  ```javascript theme={null}
  CometChat.removeAIAssistantListener("unique_listener_id");
  ```
</Warning>

#### Event descriptions

* Run Start: A new run has begun for the user's message.
* Tool Call Start: The agent decided to invoke a tool.
* Tool Call Arguments: Arguments being passed to the tool.
* Tool Call End: Tool execution completed.
* Tool Call Result: Tool's output is available.
* Card Start: The agent started generating a card. Carries `cardId` and `executionText` (a human-readable status like "Building your product card...").
* Card: The full card payload is available. Use `getCard()` to retrieve the raw card JSON and pass it to the renderer.
* Card End: The card generation flow is finalized.
* Text Message Start: The agent started composing a reply.
* Text Message Content: Streaming content chunks for progressive rendering.
* Text Message End: The agent reply is complete.
* Run Finished: The run is finalized; persisted messages will follow.

#### Card Streaming Events

When the agent generates a card, the run emits a card cycle (`Card Start` → `Card` → `Card End`). All three are `AIAssistantBaseEvent` subclasses delivered through the same `onAIAssistantEventReceived` callback — no separate listener is required.

| Class | Event type (`getType()`) | Getters |
| - | - | - |
| `AIAssistantCardStartedEvent` | `card_start` | `getCardId()`, `getExecutionText()`, `getStreamMessageId()` |
| `AIAssistantCardReceivedEvent` | `card` | `getCardId()`, `getCard()`, `getStreamMessageId()` |
| `AIAssistantCardEndedEvent` | `card_end` | `getCardId()`, `getStreamMessageId()` |

<Tabs>
  <Tab title="TypeScript">
    ```typescript theme={null}
    CometChat.addAIAssistantListener("unique_listener_id", {
      onAIAssistantEventReceived: (event: CometChat.AIAssistantBaseEvent) => {
        if (event instanceof CometChat.AIAssistantCardStartedEvent) {
          console.log("Card generation started:", event.getCardId());
          console.log("Execution text:", event.getExecutionText());
        } else if (event instanceof CometChat.AIAssistantCardReceivedEvent) {
          console.log("Card received:", event.getCardId());
          const cardPayload = event.getCard();
          // Pass cardPayload to your card renderer
        } else if (event instanceof CometChat.AIAssistantCardEndedEvent) {
          console.log("Card generation ended:", event.getCardId());
        }
      },
    });
    ```
  </Tab>

  <Tab title="JavaScript">
    ```javascript theme={null}
    CometChat.addAIAssistantListener("unique_listener_id", {
      onAIAssistantEventReceived: (event) => {
        if (event instanceof CometChat.AIAssistantCardStartedEvent) {
          console.log("Card generation started:", event.getCardId());
          console.log("Execution text:", event.getExecutionText());
        } else if (event instanceof CometChat.AIAssistantCardReceivedEvent) {
          console.log("Card received:", event.getCardId());
          const cardPayload = event.getCard();
          // Pass cardPayload to your card renderer
        } else if (event instanceof CometChat.AIAssistantCardEndedEvent) {
          console.log("Card generation ended:", event.getCardId());
        }
      },
    });
    ```
  </Tab>
</Tabs>

### Agentic Messages

After the run completes, these messages arrive via `MessageListener`:

| Message Type | Description |
| - | - |
| `AIAssistantMessage` | The full assistant reply |
| `AIToolResultMessage` | The final output of a tool call |
| `AIToolArgumentMessage` | The arguments passed to a tool |

Each message type extends [`BaseMessage`](/sdk/reference/messages#basemessage) and has a typed data accessor:

| Message Type | Data Getter | Data Properties |
| - | - | - |
| `AIAssistantMessage` | `getAssistantMessageData()` | `getRunId()`, `getThreadId()`, `getText()` |
| `AIToolResultMessage` | `getToolResultMessageData()` | `getRunId()`, `getThreadId()`, `getText()`, `getToolCallId()` |
| `AIToolArgumentMessage` | `getToolArgumentMessageData()` | `getRunId()`, `getThreadId()`, `getToolCalls()` |

The `getToolCalls()` method on `AIToolArgumentMessage` returns an array of `AIToolCall` objects, each with:

| Getter | Return Type | Description |
| - | - | - |
| `getId()` | `string` | Unique tool call ID |
| `getType()` | `string` | Tool call type |
| `getFunction()` | `AIToolCallFunction` | Function object with `getName()` and `getArguments()` |
| `getDisplayName()` | `string` | Display name of the tool |
| `getExecutionText()` | `string` | Execution description text |

<Tabs>
  <Tab title="TypeScript">
    ```ts theme={null}
    const listnerId: string = "unique_listener_id";

    // Adding the MessageListener
    CometChat.addMessageListener(listnerId, {
        onAIAssistantMessageReceived: (message: CometChat.AIAssistantMessage) => {
            console.log("AI Assistant message received successfully", message);
        },
        onAIToolResultReceived: (message: CometChat.AIToolResultMessage) => {
            console.log("AI Tool result message received successfully", message);
        },
        onAIToolArgumentsReceived: (message: CometChat.AIToolArgumentMessage) => {
            console.log("AI Tool argument message received successfully", message);
        },
    });

    // Removing the MessageListener
    CometChat.removeMessageListener(listnerId);
    ```
  </Tab>

  <Tab title="JavaScript">
    ```js theme={null}
    const listnerId = "unique_listener_id";

    // Adding the MessageListener
    CometChat.addMessageListener(listnerId, {
        onAIAssistantMessageReceived: (message) => {
            console.log("AI Assistant message received successfully", message);
        },
        onAIToolResultReceived: (message) => {
            console.log("AI Tool result message received successfully", message);
        },
        onAIToolArgumentsReceived: (message) => {
            console.log("AI Tool argument message received successfully", message);
        },
    });

    // Removing the MessageListener
    CometChat.removeMessageListener(listnerId);
    ```
  </Tab>
</Tabs>

<Warning>
  Always remove listeners when they're no longer needed (e.g., on component unmount or page navigation). Failing to remove listeners can cause memory leaks and duplicate event handling.
</Warning>

### AIAssistantMessage Elements

Starting from React Native SDK **4.0.26**, a persisted `AIAssistantMessage` carries its content as an ordered list of blocks via `getElements()`. This is the preferred render source — when present, walk the list in order and render each block. If the agent response contains only a card (no accompanying text), the text returned by `getAssistantMessageData().getText()` will be empty, so always prefer `getElements()`.

`getElements()` returns an array of `AIAssistantElement` (or `null` for older messages without elements). Each element exposes:

| Method | Return Type | Description |
| - | - | - |
| `getType()` | `string` | The block type, e.g. `"text"` or `"card"`. Determines the shape of `getData()`. |
| `getData()` | `string \| object` | The block's raw body. `"text"` → `string`; `"card"` → `{ card, cardId }`; other types → raw JSON value. The SDK never interprets this — it returns the value as-is. |

<Tabs>
  <Tab title="TypeScript">
    ```typescript theme={null}
    function handleAIAssistantMessage(message: CometChat.AIAssistantMessage) {
      const elements = message.getElements();

      if (elements && elements.length > 0) {
        // Preferred path: walk elements in order
        elements.forEach((element: CometChat.AIAssistantElement) => {
          switch (element.getType()) {
            case "text":
              console.log("Text block:", element.getData());
              break;
            case "card": {
              const { card, cardId } = element.getData() as {
                card: object;
                cardId: string;
              };
              console.log("Card block:", cardId);
              // Pass card to your card renderer
              break;
            }
            default:
              console.log("Unknown element type:", element.getType());
          }
        });
      } else {
        // Fallback for older messages without elements
        console.log("Message text:", message.getAssistantMessageData().getText());
      }
    }
    ```
  </Tab>

  <Tab title="JavaScript">
    ```javascript theme={null}
    function handleAIAssistantMessage(message) {
      const elements = message.getElements();

      if (elements && elements.length > 0) {
        elements.forEach((element) => {
          switch (element.getType()) {
            case "text":
              console.log("Text block:", element.getData());
              break;
            case "card": {
              const { card, cardId } = element.getData();
              console.log("Card block:", cardId);
              // Pass card to your card renderer
              break;
            }
            default:
              console.log("Unknown element type:", element.getType());
          }
        });
      } else {
        console.log("Message text:", message.getAssistantMessageData().getText());
      }
    }
    ```
  </Tab>
</Tabs>

***

## Next Steps

<CardGroup cols={2}>
  <Card title="AI Agents Overview" icon="robot" href="/ai-agents">
    Explore the full AI Agents platform documentation
  </Card>

  <Card title="AI Moderation" icon="shield-check" href="/sdk/react-native/ai-moderation">
    Automatically moderate messages using AI
  </Card>

  <Card title="Send Messages" icon="paper-plane" href="/sdk/react-native/send-message">
    Send text messages that trigger AI Agent responses
  </Card>
</CardGroup>


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