Back to Copilotkit

Thread

showcase/shell-docs/src/content/reference/channels/classes/Thread.mdx

1.65.08.8 KB
Original Source

A Channels Thread is the SDK handle for one native conversation. Handlers, tools, and JSX callbacks receive it.

Properties

PropertyTypeDescription
conversationKeystringStable managed conversation key. Also passed to the agent(threadId) factory.
platformstringNative delivery provider. Managed Channels report "slack" or "teams".
supportsBlockingChoiceboolean | undefinedfalse on the managed path. Use post-and-resume instead of awaitChoice.

Post and update

MethodReturnsDescription
post(ui)Promise<MessageRef>Send text or portable JSX.
update(ref, ui)Promise<MessageRef>Replace a prior message.
delete(ref)Promise<void>Remove a prior message when supported.
stream(source)Promise<MessageRef>Stream text where the adapter supports streaming.
postFile(args)Promise<{ ok, fileId?, error? }>Upload bytes with a filename when supported.
postEphemeral(user, ui, { fallbackToDM })Promise<EphemeralResult | null>Provider-capability-gated private reply. The required boolean chooses whether to fall back to a direct message.
tsx
const ref = await thread.post("Working…");
await thread.update(ref, "Done.");

The MessageRef returned by thread.post() is updateable or deletable only during the current managed delivery. Do not persist arbitrary refs and reuse them to update or delete messages across deliveries.

In a later interaction, use the interaction-provided message.ref, which Intelligence stamps for that delivery. Only attempt an update when message.ref.id is non-empty, and treat that update as best-effort.

Capability-result methods such as postFile, react, and setSuggestedPrompts can return { ok: false } when unavailable. Message operations such as update, delete, and stream can reject when the current adapter or provider cannot perform them, so catch failures when they are not allowed to fail the workflow.

Run and resume the agent

MethodReturnsDescription
runAgent(input?)Promise<MessageRef | undefined>Run the thread's agent and render its output.
resume(value, options?)Promise<MessageRef | undefined>Consume the action continuation and re-enter an interrupted run.

runAgent accepts:

FieldTypeDescription
promptstring | AgentContentPart[]Explicit user turn. When omitted in a message handler, the SDK injects the inbound text or content parts automatically.
contextContextEntry[]Context for this run only.
toolsChannelTool[]Tools for this run only.
transcriptboolean | { limit?: number }Optional SDK transcript bridge when identifyUser resolves a user and transcripts are configured.
memory{ user?, project? }Per-run Intelligence Memory access. Each scope is "none", "read", or "read-write"; omission disables Memory.
ts
channel.onMessage(async ({ thread, message }) => {
  await thread.runAgent({
    prompt: message.contentParts?.length
      ? [
          ...(message.text
            ? [{ type: "text" as const, text: message.text }]
            : []),
          ...message.contentParts,
        ]
      : message.text,
    context: [{ description: "Originating platform", value: message.platform }],
  });
});

For managed approvals, post a registered component, return from the interrupt handler, and call resume(value) when a later click arrives. Do not call awaitChoice; see the interactive messages guide for Slack or Teams.

Personal Memory on resume needs a trusted subject selector:

ts
await thread.resume(value, {
  memory: { user: "read", project: "read" },
  subject: "initiator", // or "actor"
});

initiator keeps the application user that started this HITL chain. actor uses the application user resolved for the current interaction. Project-only Memory needs no subject and carries no made-up user. A continuation expires with action retention and can start only one resumed run.

Memory and continuation failures expose stable codes:

  • channel_memory_grant_invalid, channel_memory_user_required, and channel_memory_unavailable
  • channel_memory_subject_required, channel_continuation_required, channel_continuation_mismatch, and channel_action_expired

Conversation history and users

MethodReturnsDescription
getMessages()Promise<ThreadMessage[]>Managed history in chronological order; returns [] if unavailable.
lookupUser(query)Promise<ProviderActor | undefined>Provider lookup where supported.

Per-conversation state

MethodReturnsDescription
state<T>()Promise<T | undefined>Read the value stored for this conversation.
setState<T>(value)Promise<void>Replace the full stored value. Validated when store.state is configured.

State uses the Channel's StateStore. Without a durable store.adapter, the default MemoryStore keeps it only in the current process. See the threads and state guide for Slack or Teams.

Provider-capability methods

MethodPurpose
react(ref, emoji) / unreact(ref, emoji)Add or remove the bot's reaction.
setSuggestedPrompts(prompts, options?)Set prompts on surfaces such as an assistant pane.
setTitle(title)Name the conversation.
subscribe() / unsubscribe() / isSubscribed()Store a subscription flag. Proactive routing from that flag is not implemented.

Managed Slack and Teams support react and unreact for the portable reaction set: thumbs_up, thumbs_down, heart, fire, eyes, refresh, thinking, and tada. Other methods remain provider-capability dependent; check { ok } when the method returns a capability result.