CopilotKitDocs
  • Docs
  • Reference
  • Cookbook
Get Intelligence free
CopilotKitDocs
DocsReferenceCookbook
DocsReferenceCookbook

@copilotkit/bot

Thread

@copilotkit/bot-slack

ReferencebotClasses

Thread

The per-conversation handle — post and stream messages, run the agent, block on a human choice, and reach platform power through capability-gated methods.


Overview

A Thread is the per-conversation handle passed to every handler, tool context, and interaction context. It posts UI (JSX from the component vocabulary or plain strings), drives the agent run loop, resolves human-in-the-loop choices, and exposes platform power through capability-gated methods that degrade gracefully on surfaces that don't support them.

interface Thread {
  readonly platform: string;
  post(ui: Renderable): Promise<MessageRef>;
  update(ref: MessageRef, ui: Renderable): Promise<MessageRef>;
  delete(ref: MessageRef): Promise<void>;
  stream(src: string | AsyncIterable<string>): Promise<MessageRef>;
  runAgent(input?: {
    context?: ContextEntry[];
    tools?: BotTool[];
    prompt?: string;
  }): Promise<MessageRef | undefined>;
  resume(value: unknown): Promise<MessageRef | undefined>;
  awaitChoice<T = unknown>(ui: Renderable): Promise<T>;
  getMessages(): Promise<ThreadMessage[]>;
  lookupUser(query: string): Promise<PlatformUser | undefined>;
  postFile(args: {
    bytes: Uint8Array;
    filename: string;
    title?: string;
    altText?: string;
  }): Promise<{ ok: boolean; fileId?: string; error?: string }>;
}

Properties

Prop

Type

Methods

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Usage

bot.onMention(async ({ thread, message }) => {
  // Run the agent with extra per-run context:
  await thread.runAgent({
    context: [
      { description: "Requesting user", value: message.user.name ?? message.user.id },
    ],
  });
});
// Inside a tool: read the thread, then block on approval.
async handler({ summary }, { thread }) {
  const choice = await thread.awaitChoice<{ confirmed: boolean }>(
    <ConfirmWrite action={summary} />,
  );
  return choice ?? { confirmed: false }; // serialized for the agent automatically
}

Behavior

  • Capability gating keeps tools portable — getMessages / lookupUser / postFile delegate to the adapter when supported and degrade gracefully ([] / undefined / { ok: false }) when not, so the same tool runs on any surface.
  • Per-run merging — runAgent's tools and context apply to that run only, layered on top of the bot-level defaults.
  • History reconstruction — on Slack, the conversation's agent.messages are rebuilt from Slack history each turn; the platform is the source of truth, so bot restarts don't lose conversations.

Related

  • createBot — where handlers receive a Thread
  • defineBotTool — tools receive the Thread in ctx.thread
  • Button — interactive messages and awaitChoice
  • slack() — how the Slack adapter backs these methods
570dd39