@trigger.dev/sdk 4.7.4 → 4.8.0-webhooks.20261020092920
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/commonjs/v3/ai.d.ts +626 -8
- package/dist/commonjs/v3/ai.js +2343 -185
- package/dist/commonjs/v3/ai.js.map +1 -1
- package/dist/commonjs/v3/chat.d.ts +23 -0
- package/dist/commonjs/v3/chat.js.map +1 -1
- package/dist/commonjs/v3/index.d.ts +2 -0
- package/dist/commonjs/v3/index.js +23 -17
- package/dist/commonjs/v3/index.js.map +1 -1
- package/dist/commonjs/v3/modelFileDownload.d.ts +10 -0
- package/dist/commonjs/v3/modelFileDownload.js +164 -0
- package/dist/commonjs/v3/modelFileDownload.js.map +1 -0
- package/dist/commonjs/v3/query.d.ts +434 -1
- package/dist/commonjs/v3/query.js +115 -0
- package/dist/commonjs/v3/query.js.map +1 -1
- package/dist/commonjs/v3/test/index.d.ts +2 -1
- package/dist/commonjs/v3/test/index.js +4 -1
- package/dist/commonjs/v3/test/index.js.map +1 -1
- package/dist/commonjs/v3/test/mock-channel-connector.d.ts +172 -0
- package/dist/commonjs/v3/test/mock-channel-connector.js +173 -0
- package/dist/commonjs/v3/test/mock-channel-connector.js.map +1 -0
- package/dist/commonjs/v3/test/mock-chat-agent.d.ts +81 -1
- package/dist/commonjs/v3/test/mock-chat-agent.js +137 -10
- package/dist/commonjs/v3/test/mock-chat-agent.js.map +1 -1
- package/dist/commonjs/v3/transcriptStorage.d.ts +44 -1
- package/dist/commonjs/v3/transcriptStorage.js +24 -0
- package/dist/commonjs/v3/transcriptStorage.js.map +1 -1
- package/dist/commonjs/v3/webhookWaiters.d.ts +80 -0
- package/dist/commonjs/v3/webhookWaiters.js +156 -0
- package/dist/commonjs/v3/webhookWaiters.js.map +1 -0
- package/dist/commonjs/v3/webhooks.d.ts +184 -2
- package/dist/commonjs/v3/webhooks.js +323 -1
- package/dist/commonjs/v3/webhooks.js.map +1 -1
- package/dist/commonjs/version.js +1 -1
- package/dist/esm/v3/ai.d.ts +626 -8
- package/dist/esm/v3/ai.js +2336 -184
- package/dist/esm/v3/ai.js.map +1 -1
- package/dist/esm/v3/chat.d.ts +23 -0
- package/dist/esm/v3/chat.js.map +1 -1
- package/dist/esm/v3/index.d.ts +2 -0
- package/dist/esm/v3/index.js +1 -0
- package/dist/esm/v3/index.js.map +1 -1
- package/dist/esm/v3/modelFileDownload.d.ts +10 -0
- package/dist/esm/v3/modelFileDownload.js +161 -0
- package/dist/esm/v3/modelFileDownload.js.map +1 -0
- package/dist/esm/v3/query.d.ts +434 -1
- package/dist/esm/v3/query.js +115 -0
- package/dist/esm/v3/query.js.map +1 -1
- package/dist/esm/v3/test/index.d.ts +2 -1
- package/dist/esm/v3/test/index.js +2 -1
- package/dist/esm/v3/test/index.js.map +1 -1
- package/dist/esm/v3/test/mock-channel-connector.d.ts +172 -0
- package/dist/esm/v3/test/mock-channel-connector.js +170 -0
- package/dist/esm/v3/test/mock-channel-connector.js.map +1 -0
- package/dist/esm/v3/test/mock-chat-agent.d.ts +81 -1
- package/dist/esm/v3/test/mock-chat-agent.js +137 -11
- package/dist/esm/v3/test/mock-chat-agent.js.map +1 -1
- package/dist/esm/v3/transcriptStorage.d.ts +44 -1
- package/dist/esm/v3/transcriptStorage.js +24 -0
- package/dist/esm/v3/transcriptStorage.js.map +1 -1
- package/dist/esm/v3/webhookWaiters.d.ts +80 -0
- package/dist/esm/v3/webhookWaiters.js +149 -0
- package/dist/esm/v3/webhookWaiters.js.map +1 -0
- package/dist/esm/v3/webhooks.d.ts +184 -2
- package/dist/esm/v3/webhooks.js +319 -1
- package/dist/esm/v3/webhooks.js.map +1 -1
- package/dist/esm/version.js +1 -1
- package/docs/ai-chat/actions.mdx +6 -1
- package/docs/ai-chat/backend.mdx +40 -0
- package/docs/ai-chat/patterns/redacting-telemetry.mdx +117 -0
- package/docs/ai-chat/pending-messages.mdx +2 -0
- package/docs/ai-chat/reference.mdx +53 -2
- package/docs/ai-chat/transcript-storage.mdx +1 -1
- package/docs/apikeys.mdx +6 -4
- package/docs/cli-runs-commands.mdx +2 -2
- package/docs/cli-tasks-commands.mdx +95 -0
- package/docs/config/config-file.mdx +58 -0
- package/docs/config/extensions/prismaExtension.mdx +4 -4
- package/docs/deploy-environment-variables.mdx +4 -0
- package/docs/deployment/atomic-deployment.mdx +3 -3
- package/docs/deployment/overview.mdx +1 -1
- package/docs/deployment/preview-branches.mdx +1 -1
- package/docs/github-actions.mdx +3 -3
- package/docs/limits.mdx +6 -0
- package/docs/manual-setup.mdx +1 -1
- package/docs/mcp-tools.mdx +99 -3
- package/docs/observability/dashboards.mdx +62 -0
- package/docs/runs/max-duration.mdx +4 -0
- package/docs/self-hosting/env/supervisor.mdx +1 -0
- package/docs/webhooks/channels.mdx +132 -0
- package/docs/webhooks/connect.mdx +84 -0
- package/docs/webhooks/deliveries.mdx +96 -0
- package/docs/webhooks/filters.mdx +142 -0
- package/docs/webhooks/human-in-the-loop.mdx +155 -0
- package/docs/webhooks/linear.mdx +189 -0
- package/docs/webhooks/overview.mdx +103 -0
- package/docs/webhooks/session-routing.mdx +138 -0
- package/docs/webhooks/slack.mdx +368 -0
- package/docs/webhooks/sources.mdx +221 -0
- package/docs/webhooks/waiters.mdx +194 -0
- package/package.json +4 -2
package/dist/esm/v3/ai.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
|
-
import { type AnyTask, type Task, type ApiClientConfiguration, type inferSchemaIn, type inferSchemaOut, type MachinePresetName, type RealtimeDefinedInputStream, type RealtimeDefinedStream, type TaskIdentifier, type TaskOptions, type TaskRunContext, type TaskSchema, type TaskWithSchema, type AnySessionChannel, type SessionChannelName } from "@trigger.dev/core/v3";
|
|
1
|
+
import { type AnyTask, type Task, type ApiClientConfiguration, type inferSchemaIn, type inferSchemaOut, type MachinePresetName, type RealtimeDefinedInputStream, type RealtimeDefinedStream, type TaskIdentifier, type TaskOptions, type TaskRunContext, type TaskSchema, type TaskWithSchema, type AnySessionChannel, type SessionChannelName, type AnyChatEvent, type ChatEventActions, type ValidatedWebhookKey, type ValidateWebhookFilter, type NarrowWebhookEvent, type AnyWebhookEndpoint, type InferWebhookEndpointEvent } from "@trigger.dev/core/v3";
|
|
2
2
|
import type { streamText as aiStreamTextSignature, FinishReason, LanguageModelUsage, ModelMessage, SystemModelMessage, ProviderMetadata, Tool, ToolSet, UIMessage, UIMessageChunk, UIMessageStreamOptions } from "ai";
|
|
3
|
-
import {
|
|
3
|
+
import { chatEvent } from "./webhooks.js";
|
|
4
|
+
import { type TranscriptLoadResult, type TranscriptChannelBinding, type TranscriptStorage } from "./transcriptStorage.js";
|
|
4
5
|
import { type ChatInputChunk, type ChatTaskWirePayload, type InferChatClientData, type InferChatUIMessage, type InferChatUIMessageFromTools, PENDING_MESSAGE_INJECTED_TYPE, upsertIncomingMessage } from "./ai-shared.js";
|
|
5
6
|
import { locals } from "./locals.js";
|
|
6
7
|
import type { ResolvedPrompt } from "./prompt.js";
|
|
@@ -33,6 +34,7 @@ type ChatTurnContext<TClientData = unknown> = {
|
|
|
33
34
|
turn: number;
|
|
34
35
|
continuation: boolean;
|
|
35
36
|
clientData?: TClientData;
|
|
37
|
+
recordUserMessage?: boolean;
|
|
36
38
|
};
|
|
37
39
|
export { __readChatSnapshotProductionPathForTests, __setReadChatSnapshotImplForTests, __setWriteChatSnapshotImplForTests, __writeChatSnapshotProductionPathForTests, } from "./chatSnapshotIo.js";
|
|
38
40
|
export { defaultStorage, memoryTranscriptStorage, reduceTranscriptChanges, snapshotTranscriptStorage, type LoadContextEvent, type MemoryTranscriptStorage, type TranscriptChange, type TranscriptChangeReason, type TranscriptChangeset, type TranscriptCursors, type TranscriptLoadOptions, type TranscriptLoadResult, type TranscriptScope, type TranscriptState, type TranscriptStorage, type TranscriptStorageContext, } from "./transcriptStorage.js";
|
|
@@ -149,6 +151,31 @@ export declare const ai: {
|
|
|
149
151
|
* ```
|
|
150
152
|
*/
|
|
151
153
|
declare function createChatAccessToken<TTask extends AnyTask>(taskId: TaskIdentifier<TTask>): Promise<string>;
|
|
154
|
+
/**
|
|
155
|
+
* Mint a read-only, session-scoped token for WATCHING a chat session by its `externalId`.
|
|
156
|
+
*
|
|
157
|
+
* A session is addressed by `externalId`, so the same session is reachable from any surface that
|
|
158
|
+
* knows it: a web `useChat` client and a Slack thread converge on one session when they share an
|
|
159
|
+
* `externalId` (for a channel, the connector's `key` template produces it). This token carries
|
|
160
|
+
* `read:sessions:{externalId}` only (no write): the holder can subscribe to the session's `.out`
|
|
161
|
+
* stream (observe the conversation, hydrating history from the snapshot) but cannot append to `.in`.
|
|
162
|
+
*
|
|
163
|
+
* Use it for a dashboard viewer or a cross-surface watcher of a Slack-thread session. Run server-side
|
|
164
|
+
* (needs the secret key). To CONTINUE a session from another surface (drive it, not just watch), mint
|
|
165
|
+
* a read+write token instead ({@link createChatStartSessionAction}).
|
|
166
|
+
*
|
|
167
|
+
* @example
|
|
168
|
+
* ```ts
|
|
169
|
+
* // actions.ts
|
|
170
|
+
* "use server";
|
|
171
|
+
* import { chat } from "@trigger.dev/sdk/ai";
|
|
172
|
+
*
|
|
173
|
+
* export const watchChat = (externalId: string) => chat.createWatchToken(externalId);
|
|
174
|
+
* ```
|
|
175
|
+
*/
|
|
176
|
+
declare function createChatWatchToken(externalId: string, options?: {
|
|
177
|
+
tokenTTL?: string;
|
|
178
|
+
}): Promise<string>;
|
|
152
179
|
/**
|
|
153
180
|
* Register work that must land before anything from this turn reaches the
|
|
154
181
|
* frontend.
|
|
@@ -308,6 +335,12 @@ export type ChatTaskRunPayload<TClientData = unknown, TTools extends ToolSet = T
|
|
|
308
335
|
* `tools` option on `chat.agent`). Empty object when no `tools` were declared.
|
|
309
336
|
*/
|
|
310
337
|
tools: TTools;
|
|
338
|
+
/**
|
|
339
|
+
* Present for a channel turn whose connector supports reactions or defines a `surface()`. Lets the
|
|
340
|
+
* agent react to the triggering message (e.g. `channel.react("white_check_mark")`) and use the
|
|
341
|
+
* connector's helpers (cast to the connector's exported surface type).
|
|
342
|
+
*/
|
|
343
|
+
channel?: ChannelRunSurface;
|
|
311
344
|
};
|
|
312
345
|
/**
|
|
313
346
|
* One message record delivered through {@link chat.messages}.
|
|
@@ -1042,6 +1075,8 @@ declare const actionTurnBrand: unique symbol;
|
|
|
1042
1075
|
*/
|
|
1043
1076
|
export type ActionTurn = {
|
|
1044
1077
|
readonly [actionTurnBrand]: true;
|
|
1078
|
+
/** A user message the turn answers, appended to the history after the action's edit. */
|
|
1079
|
+
readonly message?: string | UIMessage;
|
|
1045
1080
|
};
|
|
1046
1081
|
/**
|
|
1047
1082
|
* Turn the current action into a turn.
|
|
@@ -1054,6 +1089,9 @@ export type ActionTurn = {
|
|
|
1054
1089
|
* tools, steering, compaction, injected instructions and persistence, with no
|
|
1055
1090
|
* action-specific handling.
|
|
1056
1091
|
*
|
|
1092
|
+
* Pass `message` to have the turn answer a new user message, appended after the edit: a click on a
|
|
1093
|
+
* "Explain more" button becomes `chat.turn("Explain that in more detail.")`.
|
|
1094
|
+
*
|
|
1057
1095
|
* @example
|
|
1058
1096
|
* ```ts
|
|
1059
1097
|
* onAction: async ({ action }) => {
|
|
@@ -1061,11 +1099,12 @@ export type ActionTurn = {
|
|
|
1061
1099
|
* chat.history.slice(0, -1);
|
|
1062
1100
|
* return chat.turn();
|
|
1063
1101
|
* }
|
|
1102
|
+
* if (action.type === "ask") return chat.turn(action.question);
|
|
1064
1103
|
* if (action.type === "undo") chat.history.slice(0, -2); // no turn
|
|
1065
1104
|
* },
|
|
1066
1105
|
* ```
|
|
1067
1106
|
*/
|
|
1068
|
-
declare function chatTurn(): ActionTurn;
|
|
1107
|
+
declare function chatTurn(message?: string | UIMessage): ActionTurn;
|
|
1069
1108
|
/**
|
|
1070
1109
|
* Pipes a chat stream to the realtime stream, making it available to the
|
|
1071
1110
|
* `TriggerChatTransport` on the frontend.
|
|
@@ -1408,6 +1447,18 @@ export type ActionEvent<TAction = unknown, TClientData = unknown, TUIM extends U
|
|
|
1408
1447
|
uiMessages: TUIM[];
|
|
1409
1448
|
/** The accumulated model messages (after hydration, if set). */
|
|
1410
1449
|
messages: ModelMessage[];
|
|
1450
|
+
/**
|
|
1451
|
+
* The click that sent a channel action (a `slackButton()` in Slack): the verified provider event,
|
|
1452
|
+
* with who clicked and the message the button was on. Absent for client and webhook actions.
|
|
1453
|
+
*/
|
|
1454
|
+
channel?: ChannelActionSource;
|
|
1455
|
+
};
|
|
1456
|
+
/** Where a channel action came from: the connector and the verified event of the click. */
|
|
1457
|
+
export type ChannelActionSource = {
|
|
1458
|
+
connectorId: string;
|
|
1459
|
+
provider: string;
|
|
1460
|
+
event: unknown;
|
|
1461
|
+
deliveryId: string;
|
|
1411
1462
|
};
|
|
1412
1463
|
/**
|
|
1413
1464
|
* Event passed to the `onTurnStart` callback.
|
|
@@ -1632,7 +1683,504 @@ export type ChatResumeEvent<TClientData = unknown, TUIM extends UIMessage = UIMe
|
|
|
1632
1683
|
/** Custom data from the frontend. */
|
|
1633
1684
|
clientData?: TClientData;
|
|
1634
1685
|
};
|
|
1635
|
-
export type
|
|
1686
|
+
export type ChannelMessageInput = string | UIMessage;
|
|
1687
|
+
/**
|
|
1688
|
+
* What a connector's `inbound()` returns: the turn's message, optionally with who sent it on
|
|
1689
|
+
* the provider and the provider's own message id. Both land on the user message's `metadata`
|
|
1690
|
+
* (with `source: "channel"`, the connector id, the provider and the delivery id), so a
|
|
1691
|
+
* transcript storage can attribute and reconcile channel messages.
|
|
1692
|
+
*/
|
|
1693
|
+
export type ChannelInbound = ChannelMessageInput | {
|
|
1694
|
+
message: ChannelMessageInput;
|
|
1695
|
+
externalUserId?: string;
|
|
1696
|
+
externalMessageId?: string;
|
|
1697
|
+
};
|
|
1698
|
+
/** The `metadata` the runtime stamps on a channel-delivered user message. */
|
|
1699
|
+
export type ChannelMessageMetadata = {
|
|
1700
|
+
source: "channel";
|
|
1701
|
+
connectorId: string;
|
|
1702
|
+
provider: string;
|
|
1703
|
+
/** The delivery that carried the message (`whd_...`). */
|
|
1704
|
+
deliveryId: string;
|
|
1705
|
+
/** The provider's id for that delivery, the same across replays. */
|
|
1706
|
+
externalDeliveryId?: string;
|
|
1707
|
+
externalUserId?: string;
|
|
1708
|
+
externalMessageId?: string;
|
|
1709
|
+
/** True on a message the connector supplied from the surface's existing conversation via `seed()`. */
|
|
1710
|
+
seeded?: boolean;
|
|
1711
|
+
};
|
|
1712
|
+
/**
|
|
1713
|
+
* A prior message from the surface, returned by a connector's `seed()` when a session starts on a
|
|
1714
|
+
* conversation that already has history (a Slack thread the bot was summoned into). Becomes a
|
|
1715
|
+
* transcript message ahead of the triggering one, so the agent can answer with the context a human
|
|
1716
|
+
* reading the thread would have.
|
|
1717
|
+
*/
|
|
1718
|
+
export type ChannelSeedMessage = {
|
|
1719
|
+
role: "user" | "assistant";
|
|
1720
|
+
text: string;
|
|
1721
|
+
/** The provider's id for the message; used as the transcript message id suffix and kept in metadata. */
|
|
1722
|
+
externalMessageId?: string;
|
|
1723
|
+
externalUserId?: string;
|
|
1724
|
+
};
|
|
1725
|
+
export type ChannelSeedCtx<TEvent = unknown> = {
|
|
1726
|
+
event: TEvent;
|
|
1727
|
+
deliveryId: string;
|
|
1728
|
+
};
|
|
1729
|
+
/** A file a connector fetched for the model: its bytes, and the media type when the surface reports one. */
|
|
1730
|
+
export type ChannelDownloadedFile = {
|
|
1731
|
+
data: Uint8Array;
|
|
1732
|
+
mediaType?: string;
|
|
1733
|
+
};
|
|
1734
|
+
/**
|
|
1735
|
+
* The channel a session answers into, once a channel turn has bound it. The connector's
|
|
1736
|
+
* `bind()` derives the handle from a verified event; later turns that did not start from a
|
|
1737
|
+
* channel delivery (a `chat.event` action that returns `chat.turn()`, a browser message on the
|
|
1738
|
+
* same session) egress through it.
|
|
1739
|
+
*/
|
|
1740
|
+
export type ChannelBinding<THandle = unknown> = TranscriptChannelBinding<THandle>;
|
|
1741
|
+
export type ChannelMessage = {
|
|
1742
|
+
text: string;
|
|
1743
|
+
[key: string]: unknown;
|
|
1744
|
+
};
|
|
1745
|
+
export type ChannelReply = {
|
|
1746
|
+
text: string;
|
|
1747
|
+
message: UIMessage;
|
|
1748
|
+
final: boolean;
|
|
1749
|
+
stopped: boolean;
|
|
1750
|
+
error?: unknown;
|
|
1751
|
+
/**
|
|
1752
|
+
* True when the turn paused on a human decision: this text is what the agent wrote before calling
|
|
1753
|
+
* the tool, and the controls follow as their own message. A surface with a notion of "done" (Linear
|
|
1754
|
+
* sessions) should post it as progress rather than as the answer.
|
|
1755
|
+
*/
|
|
1756
|
+
pending?: boolean;
|
|
1757
|
+
};
|
|
1758
|
+
export type ChannelSendCtx<TEvent = unknown, THandle = unknown> = {
|
|
1759
|
+
/** The verified event that started this turn. Absent on a bound turn that no channel delivery started. */
|
|
1760
|
+
event?: TEvent;
|
|
1761
|
+
/** The connector's posting handle from `bind()`, when the connector defines one. */
|
|
1762
|
+
handle?: THandle;
|
|
1763
|
+
/** The delivery that started this turn. Absent on a bound turn. */
|
|
1764
|
+
deliveryId?: string;
|
|
1765
|
+
previousRef?: string;
|
|
1766
|
+
mode: "final" | "stream";
|
|
1767
|
+
final: boolean;
|
|
1768
|
+
/** True when this turn was not started by a channel delivery and egresses through the session's binding. */
|
|
1769
|
+
bound: boolean;
|
|
1770
|
+
};
|
|
1771
|
+
export type ChannelAckCtx = {
|
|
1772
|
+
/**
|
|
1773
|
+
* True when this ack is being re-posted because the run is recovering an
|
|
1774
|
+
* interrupted turn after a crash/continuation. The prior run's message ref
|
|
1775
|
+
* is gone, so egress re-emits into the thread as a fresh message; a
|
|
1776
|
+
* connector can vary the placeholder text to read as a deliberate resume
|
|
1777
|
+
* ("picking this back up...") rather than a silent duplicate.
|
|
1778
|
+
*/
|
|
1779
|
+
recovered: boolean;
|
|
1780
|
+
};
|
|
1781
|
+
/**
|
|
1782
|
+
* A tool call the turn paused on, awaiting a human decision (HITL). `renderInteraction` maps these to
|
|
1783
|
+
* the controls posted in the thread; the callback resolves one by `toolCallId`.
|
|
1784
|
+
*/
|
|
1785
|
+
export type ChannelPendingToolCall = {
|
|
1786
|
+
toolCallId: string;
|
|
1787
|
+
toolName: string;
|
|
1788
|
+
input?: unknown;
|
|
1789
|
+
};
|
|
1790
|
+
/**
|
|
1791
|
+
* A verified interaction callback resolved to a tool output. `onInteraction` returns this to resume the
|
|
1792
|
+
* paused run: the framework stitches `output` onto the pending tool part and continues. Name the call
|
|
1793
|
+
* by `toolCallId` when the surface can carry it (a Slack button value), or by `toolName` when it cannot
|
|
1794
|
+
* (a Linear option whose value the user sees); the most recent pending call of that tool is resolved.
|
|
1795
|
+
*/
|
|
1796
|
+
export type ChannelInteractionResolution = {
|
|
1797
|
+
toolCallId: string;
|
|
1798
|
+
toolName?: string;
|
|
1799
|
+
output: unknown;
|
|
1800
|
+
} | {
|
|
1801
|
+
toolName: string;
|
|
1802
|
+
toolCallId?: string;
|
|
1803
|
+
output: unknown;
|
|
1804
|
+
};
|
|
1805
|
+
/**
|
|
1806
|
+
* Context for `renderInteraction`: the event and delivery that started the turn, both absent on a
|
|
1807
|
+
* bound turn (a `chat.turn()` action or a browser message answering into the bound thread).
|
|
1808
|
+
*/
|
|
1809
|
+
export type ChannelInteractionCtx<TEvent = unknown> = {
|
|
1810
|
+
event?: TEvent;
|
|
1811
|
+
deliveryId?: string;
|
|
1812
|
+
};
|
|
1813
|
+
export type ChannelReaction = {
|
|
1814
|
+
name: string;
|
|
1815
|
+
remove?: boolean;
|
|
1816
|
+
};
|
|
1817
|
+
export type ChannelReactCtx<TEvent = unknown> = {
|
|
1818
|
+
event: TEvent;
|
|
1819
|
+
deliveryId: string;
|
|
1820
|
+
};
|
|
1821
|
+
export type ChannelReactionChoice<TEvent = unknown> = string | string[] | ((event: TEvent) => string | string[] | null | undefined | Promise<string | string[] | null | undefined>);
|
|
1822
|
+
export type ChannelReactions<TEvent = unknown> = {
|
|
1823
|
+
working?: ChannelReactionChoice<TEvent>;
|
|
1824
|
+
done?: ChannelReactionChoice<TEvent>;
|
|
1825
|
+
error?: ChannelReactionChoice<TEvent>;
|
|
1826
|
+
};
|
|
1827
|
+
export type ChannelRunSurface<TExtra extends Record<string, unknown> = Record<string, unknown>> = {
|
|
1828
|
+
react: (name: string) => Promise<void>;
|
|
1829
|
+
unreact: (name: string) => Promise<void>;
|
|
1830
|
+
} & TExtra;
|
|
1831
|
+
/**
|
|
1832
|
+
* The turn a connector hook is running in: the verified event and delivery that started it (absent on
|
|
1833
|
+
* a bound turn), and the session's posting handle from `bind()` when the connector defines one.
|
|
1834
|
+
*/
|
|
1835
|
+
export type ChannelTurnCtx<TEvent = unknown, THandle = unknown> = {
|
|
1836
|
+
event?: TEvent;
|
|
1837
|
+
handle?: THandle;
|
|
1838
|
+
deliveryId?: string;
|
|
1839
|
+
/** True when no channel delivery started this turn and it egresses through the session's binding. */
|
|
1840
|
+
bound: boolean;
|
|
1841
|
+
};
|
|
1842
|
+
/**
|
|
1843
|
+
* What a connector's `onControl()` maps a verified event to. `stop` aborts the turn in flight through
|
|
1844
|
+
* the same per-turn stop signal the browser's stop button uses: the run's `stopSignal` fires,
|
|
1845
|
+
* `streamText` aborts, the partial reply posts with `stopped: true`, and the event itself is consumed
|
|
1846
|
+
* (it does not run as a turn).
|
|
1847
|
+
*
|
|
1848
|
+
* `whenIdle` decides what a stop does when no turn is in flight. `"message"` (the default) handles
|
|
1849
|
+
* the event as a normal inbound message, so the connector's `inbound()` should give it a sensible
|
|
1850
|
+
* reading. `"drop"` consumes it without a turn; if the session is paused on a human decision, the
|
|
1851
|
+
* pending tool calls are resolved as stopped (a later approval click finds nothing to resume) and
|
|
1852
|
+
* the connector's `cancelInteraction()` updates the controls.
|
|
1853
|
+
*
|
|
1854
|
+
* `at` is when the user asked to stop (epoch milliseconds). A stop older than the running turn's
|
|
1855
|
+
* start belongs to an earlier turn: it is consumed without aborting this one.
|
|
1856
|
+
*/
|
|
1857
|
+
export type ChannelControl = {
|
|
1858
|
+
kind: "stop";
|
|
1859
|
+
message?: string;
|
|
1860
|
+
whenIdle?: "message" | "drop";
|
|
1861
|
+
at?: number;
|
|
1862
|
+
};
|
|
1863
|
+
/**
|
|
1864
|
+
* What a connector's `progress()` hook observes while a turn streams: each tool call as its input is
|
|
1865
|
+
* complete, and each result or error as it lands. Text deltas are not reported (use `delivery: "stream"`).
|
|
1866
|
+
* `title` is the tool's display title (`tool({ title })`), when it declares one.
|
|
1867
|
+
*/
|
|
1868
|
+
export type ChannelProgressEvent = {
|
|
1869
|
+
type: "tool-call";
|
|
1870
|
+
toolCallId: string;
|
|
1871
|
+
toolName: string;
|
|
1872
|
+
title?: string;
|
|
1873
|
+
input: unknown;
|
|
1874
|
+
} | {
|
|
1875
|
+
type: "tool-result";
|
|
1876
|
+
toolCallId: string;
|
|
1877
|
+
toolName: string;
|
|
1878
|
+
title?: string;
|
|
1879
|
+
output: unknown;
|
|
1880
|
+
} | {
|
|
1881
|
+
type: "tool-error";
|
|
1882
|
+
toolCallId: string;
|
|
1883
|
+
toolName: string;
|
|
1884
|
+
title?: string;
|
|
1885
|
+
errorText: string;
|
|
1886
|
+
};
|
|
1887
|
+
/**
|
|
1888
|
+
* Where a channel session stands, reported to a connector's `lifecycle()` hook: `working` when a turn
|
|
1889
|
+
* starts (and again every 50 minutes while it runs), `waiting` when it pauses on a human decision,
|
|
1890
|
+
* `idle` when it ends for any reason (answered, empty, stopped or failed), and `closed` when the
|
|
1891
|
+
* conversation is closed with `chat.close()`. A worker suspending between messages reports nothing.
|
|
1892
|
+
*/
|
|
1893
|
+
export type ChannelLifecycleState = "working" | "waiting" | "idle" | "closed";
|
|
1894
|
+
export type ChannelLifecycleCtx<TEvent = unknown, THandle = unknown> = ChannelTurnCtx<TEvent, THandle> & {
|
|
1895
|
+
/** True on the session's first turn, when the surface creates its conversation. */
|
|
1896
|
+
firstTurn: boolean;
|
|
1897
|
+
/** The turn's user message text, when it has one (a title for the conversation). */
|
|
1898
|
+
prompt?: string;
|
|
1899
|
+
/** True on the periodic `working` re-send during a long turn. */
|
|
1900
|
+
refresh?: boolean;
|
|
1901
|
+
};
|
|
1902
|
+
/** How a turn's reply stream ended, handed to {@link ChannelReplyStream.end}. */
|
|
1903
|
+
export type ChannelReplyStreamEnd = {
|
|
1904
|
+
/** The turn was stopped (the partial reply is all there is). */
|
|
1905
|
+
stopped: boolean;
|
|
1906
|
+
/** The turn paused on a human decision; the controls follow as their own message. */
|
|
1907
|
+
pending: boolean;
|
|
1908
|
+
/** The connector's error line (`errorMessage`) when the turn ended on a model or stream error. */
|
|
1909
|
+
errorText?: string;
|
|
1910
|
+
};
|
|
1911
|
+
/**
|
|
1912
|
+
* A connector's native streaming transport for one turn, from its `stream()` hook, used when the
|
|
1913
|
+
* connector's `delivery` is `"stream"`. The runtime feeds it the reply's text deltas as the model
|
|
1914
|
+
* writes them (in the model's markdown) and the turn's tool progress, then ends it exactly once.
|
|
1915
|
+
* `end()` resolves `delivered: true` when the reply reached the surface through the stream, so the
|
|
1916
|
+
* runtime does not post it again; `false` (nothing was streamed) falls back to `send()`.
|
|
1917
|
+
*/
|
|
1918
|
+
export type ChannelReplyStream = {
|
|
1919
|
+
text(delta: string): void;
|
|
1920
|
+
progress?(event: ChannelProgressEvent): void;
|
|
1921
|
+
end(outcome: ChannelReplyStreamEnd): Promise<{
|
|
1922
|
+
delivered: boolean;
|
|
1923
|
+
}>;
|
|
1924
|
+
};
|
|
1925
|
+
/**
|
|
1926
|
+
* What a connector's `stream()` hook receives: the turn, and `opened(ref)` to call once the surface
|
|
1927
|
+
* has created the stream message. The ref is saved with the session while the turn runs, so if the
|
|
1928
|
+
* worker dies mid-stream the next worker can end that stream with `endInterruptedStream()`.
|
|
1929
|
+
*/
|
|
1930
|
+
export type ChannelStreamCtx<TEvent = unknown, THandle = unknown> = ChannelTurnCtx<TEvent, THandle> & {
|
|
1931
|
+
opened(ref: string): void;
|
|
1932
|
+
};
|
|
1933
|
+
/** A pending tool call a stop cancelled, with the `ref` of the controls message that showed it. */
|
|
1934
|
+
export type ChannelCancelledToolCall = ChannelPendingToolCall & {
|
|
1935
|
+
ref?: string;
|
|
1936
|
+
};
|
|
1937
|
+
export type ResolveChannelToken<TEvent = unknown> = (event: TEvent) => Promise<string>;
|
|
1938
|
+
declare const channelEventPhantom: unique symbol;
|
|
1939
|
+
export interface ChannelConnector<TEvent = unknown, THandle = unknown> {
|
|
1940
|
+
id: string;
|
|
1941
|
+
/** The endpoint this connector subscribes to (`webhooks.endpoint.define` id). */
|
|
1942
|
+
endpointId: string;
|
|
1943
|
+
source: string;
|
|
1944
|
+
key: string;
|
|
1945
|
+
filter?: string;
|
|
1946
|
+
startOn?: string;
|
|
1947
|
+
inbound: (event: TEvent) => ChannelInbound;
|
|
1948
|
+
/**
|
|
1949
|
+
* Derive the durable posting handle from a verified event (for Slack: team, channel, thread). When
|
|
1950
|
+
* set, a channel turn binds the session to this connector, and later turns on the session that no
|
|
1951
|
+
* channel delivery started (an action turn, a browser message) post their answer through `send`
|
|
1952
|
+
* with `ctx.handle` and no `ctx.event`. Return null to leave the binding unchanged.
|
|
1953
|
+
*/
|
|
1954
|
+
bind?: (event: TEvent) => THandle | null;
|
|
1955
|
+
/**
|
|
1956
|
+
* Supply the surface's existing conversation when a session starts on it (the bot was summoned
|
|
1957
|
+
* into a thread that already has messages). Called once, on the first channel turn of a session
|
|
1958
|
+
* with no history, before the triggering message is added. Return the prior messages in order,
|
|
1959
|
+
* excluding the triggering one. Best effort: a throw is logged and the session starts empty.
|
|
1960
|
+
*/
|
|
1961
|
+
seed?: (event: TEvent, ctx: ChannelSeedCtx<TEvent>) => Promise<ChannelSeedMessage[]> | ChannelSeedMessage[];
|
|
1962
|
+
outbound?: (reply: ChannelReply) => ChannelMessage | null;
|
|
1963
|
+
ack?: (event: TEvent, ctx: ChannelAckCtx) => ChannelMessage | null;
|
|
1964
|
+
send?: (message: ChannelMessage, ctx: ChannelSendCtx<TEvent, THandle>) => Promise<{
|
|
1965
|
+
ref?: string;
|
|
1966
|
+
}>;
|
|
1967
|
+
/** HITL: controls posted when a turn pauses on a human-decision tool (a tool with no `execute`). */
|
|
1968
|
+
renderInteraction?: (pending: ChannelPendingToolCall[], ctx: ChannelInteractionCtx<TEvent>) => ChannelMessage | null;
|
|
1969
|
+
/**
|
|
1970
|
+
* HITL: map a verified callback event to a tool resolution. Non-null resumes the paused run; null
|
|
1971
|
+
* means treat the event as a normal inbound message (a new turn).
|
|
1972
|
+
*/
|
|
1973
|
+
onInteraction?: (event: TEvent) => ChannelInteractionResolution | null;
|
|
1974
|
+
/**
|
|
1975
|
+
* HITL: finalize the posted controls once a decision is made (edit them away, show the outcome), so
|
|
1976
|
+
* the buttons can't be clicked again. Called with the same verified callback event when
|
|
1977
|
+
* `onInteraction` resolves, before the run resumes. Best-effort: a throw is logged and the run continues.
|
|
1978
|
+
*/
|
|
1979
|
+
finalizeInteraction?: (event: TEvent, resolution: ChannelInteractionResolution) => Promise<void> | void;
|
|
1980
|
+
/**
|
|
1981
|
+
* "final": the ack, then one post (or edit of the ack) when the turn ends. "stream": the connector's
|
|
1982
|
+
* `stream()` transport when it has one, otherwise debounced edits of the ack.
|
|
1983
|
+
*/
|
|
1984
|
+
delivery: "final" | "stream";
|
|
1985
|
+
/**
|
|
1986
|
+
* Native streaming for `delivery: "stream"`: open a {@link ChannelReplyStream} for this turn. Called
|
|
1987
|
+
* once per turn that runs the model; return null to fall back to `send()` for this turn.
|
|
1988
|
+
*/
|
|
1989
|
+
stream?: (ctx: ChannelStreamCtx<TEvent, THandle>) => ChannelReplyStream | null;
|
|
1990
|
+
/**
|
|
1991
|
+
* A worker booted on a session whose previous worker died with a reply stream open (the `ref` it
|
|
1992
|
+
* passed to `opened()`). End that stream so it does not look like the agent is still writing; the
|
|
1993
|
+
* recovered turn answers in a new one. Best effort: a throw is logged.
|
|
1994
|
+
*/
|
|
1995
|
+
endInterruptedStream?: (ref: string, ctx: ChannelTurnCtx<TEvent, THandle>) => Promise<void> | void;
|
|
1996
|
+
/**
|
|
1997
|
+
* Fetch a file URL from the surface for the model, for files only the surface's credentials can
|
|
1998
|
+
* read (a Slack `url_private`). The `streamText` given to `run()` calls it for every file URL in
|
|
1999
|
+
* the prompt; return null for a URL this connector does not own. Throw when an owned file cannot
|
|
2000
|
+
* be read: the turn replaces it with a short note and still runs. `handle` is the session's
|
|
2001
|
+
* binding to this connector, when it has one.
|
|
2002
|
+
*/
|
|
2003
|
+
download?: (url: URL, ctx: {
|
|
2004
|
+
handle?: THandle;
|
|
2005
|
+
}) => Promise<ChannelDownloadedFile | null>;
|
|
2006
|
+
/**
|
|
2007
|
+
* Acknowledge a message that arrives while a turn is running, as soon as it arrives: it is either
|
|
2008
|
+
* folded into the running turn (`pendingMessages`) or answered right after it, so the wording
|
|
2009
|
+
* should be true either way (`slack()` reacts with 👀, `linear()` posts a thought). Not called for
|
|
2010
|
+
* stops, interaction clicks or empty messages. Called without waiting; a throw is ignored.
|
|
2011
|
+
* `ctx.event` is the message's event.
|
|
2012
|
+
*/
|
|
2013
|
+
received?: (ctx: ChannelTurnCtx<TEvent, THandle>) => Promise<void> | void;
|
|
2014
|
+
/**
|
|
2015
|
+
* Map a click on a control the agent posted (not a pending tool's control) to an action for the
|
|
2016
|
+
* agent's `onAction`, validated against `actionSchema` like a client action. Return null for
|
|
2017
|
+
* anything else. Returning `chat.turn()` from `onAction` answers into the session's thread.
|
|
2018
|
+
*/
|
|
2019
|
+
toAction?: (event: TEvent) => unknown | null;
|
|
2020
|
+
/**
|
|
2021
|
+
* Mirror the session's state into the surface (a Slack agent session's status). See
|
|
2022
|
+
* {@link ChannelLifecycleState}. Calls are serialized in order; a throw is logged and never
|
|
2023
|
+
* affects the turn.
|
|
2024
|
+
*/
|
|
2025
|
+
lifecycle?: (state: ChannelLifecycleState, ctx: ChannelLifecycleCtx<TEvent, THandle>) => Promise<void> | void;
|
|
2026
|
+
/**
|
|
2027
|
+
* HITL: a stop (`whenIdle: "drop"`) arrived while the session was paused on these tool calls. They
|
|
2028
|
+
* are already resolved as stopped; update the controls so they no longer offer a decision.
|
|
2029
|
+
* Best effort: a throw is logged.
|
|
2030
|
+
*/
|
|
2031
|
+
cancelInteraction?: (cancelled: ChannelCancelledToolCall[], ctx: ChannelTurnCtx<TEvent, THandle>) => Promise<void> | void;
|
|
2032
|
+
react?: (reaction: ChannelReaction, ctx: ChannelReactCtx<TEvent>) => Promise<void>;
|
|
2033
|
+
reactions?: ChannelReactions<TEvent>;
|
|
2034
|
+
/**
|
|
2035
|
+
* What the channel shows when a turn fails, in place of the error text: a fixed line, or a
|
|
2036
|
+
* function of the failure that returns one. Defaults to {@link CHANNEL_TURN_ERROR_MESSAGE}. The
|
|
2037
|
+
* error itself is logged on the run, and `outbound()` still receives it as `reply.error`.
|
|
2038
|
+
*/
|
|
2039
|
+
errorMessage?: ChannelErrorMessage<TEvent>;
|
|
2040
|
+
/**
|
|
2041
|
+
* Observe tool calls and results as the turn streams, to post progress into the surface (a Linear
|
|
2042
|
+
* `action` activity, a Slack status). Called in order, awaited one at a time, independent of
|
|
2043
|
+
* `delivery`. Best effort: a throw is logged and the turn continues.
|
|
2044
|
+
*/
|
|
2045
|
+
progress?: (event: ChannelProgressEvent, ctx: ChannelTurnCtx<TEvent, THandle>) => Promise<void> | void;
|
|
2046
|
+
/**
|
|
2047
|
+
* Provider helpers merged into the `channel` object handed to `run()` (alongside `react`/`unreact`),
|
|
2048
|
+
* such as a plan or a status setter. Built once per turn.
|
|
2049
|
+
*/
|
|
2050
|
+
surface?: (ctx: ChannelTurnCtx<TEvent, THandle>) => Record<string, unknown>;
|
|
2051
|
+
/**
|
|
2052
|
+
* Map a verified event to a control instruction while a turn is running (a Stop in Linear, a
|
|
2053
|
+
* "stop" slash command in Slack). See {@link ChannelControl}. Return null for an ordinary message.
|
|
2054
|
+
*/
|
|
2055
|
+
onControl?: (event: TEvent) => ChannelControl | null;
|
|
2056
|
+
readonly [channelEventPhantom]?: TEvent;
|
|
2057
|
+
}
|
|
2058
|
+
export type AnyChannelConnector = ChannelConnector<any, any>;
|
|
2059
|
+
/** The line a channel shows when a turn fails, unless the connector sets its own `errorMessage`. */
|
|
2060
|
+
export declare const CHANNEL_TURN_ERROR_MESSAGE = "Something went wrong answering this. Try again.";
|
|
2061
|
+
/** What an `errorMessage` function receives when a channel turn fails. */
|
|
2062
|
+
export type ChannelErrorContext<TEvent = unknown> = {
|
|
2063
|
+
/** The failure: the model or stream error, or what the turn threw. */
|
|
2064
|
+
error: Error;
|
|
2065
|
+
/** The text the turn streamed before it failed; empty when it failed before answering. */
|
|
2066
|
+
partialText: string;
|
|
2067
|
+
/** The event that started the turn; undefined on a turn the channel did not start (an action turn, a browser message). */
|
|
2068
|
+
event: TEvent | undefined;
|
|
2069
|
+
/** The run the turn failed in, for a support reference. */
|
|
2070
|
+
runId: string | undefined;
|
|
2071
|
+
/** The session's chat id. */
|
|
2072
|
+
chatId: string;
|
|
2073
|
+
/** {@link CHANNEL_TURN_ERROR_MESSAGE}, to extend rather than replace. */
|
|
2074
|
+
defaultMessage: string;
|
|
2075
|
+
};
|
|
2076
|
+
/**
|
|
2077
|
+
* A channel's error line: a fixed string, or a function of the failure. A function that returns
|
|
2078
|
+
* nothing, or throws, falls back to {@link CHANNEL_TURN_ERROR_MESSAGE}.
|
|
2079
|
+
*
|
|
2080
|
+
* @example
|
|
2081
|
+
* ```ts
|
|
2082
|
+
* errorMessage: ({ error, runId }) =>
|
|
2083
|
+
* error.name === "RateLimitError" ? "I'm a bit busy, try again in a minute." : `That failed (ref ${runId}).`,
|
|
2084
|
+
* ```
|
|
2085
|
+
*/
|
|
2086
|
+
export type ChannelErrorMessage<TEvent = unknown> = string | ((ctx: ChannelErrorContext<TEvent>) => string | null | undefined | Promise<string | null | undefined>);
|
|
2087
|
+
/**
|
|
2088
|
+
* A generic chat-frontend channel over any verified source. Unlike `slack()`, you supply the egress
|
|
2089
|
+
* `send` yourself (post/edit the reply back to your surface), so the whole round-trip is under your
|
|
2090
|
+
* control. Use for providers without a preset, or to test the channel round-trip end to end.
|
|
2091
|
+
*/
|
|
2092
|
+
export declare function chatChannelCustom<TEndpoint extends AnyWebhookEndpoint, const TKey extends string = string, const TFilter extends string = string, const TStartOn extends string = string, THandle = unknown>(options: {
|
|
2093
|
+
id: string;
|
|
2094
|
+
/** The endpoint this connector subscribes to. */
|
|
2095
|
+
endpoint: TEndpoint;
|
|
2096
|
+
/**
|
|
2097
|
+
* The session each delivery goes to, as a template: `{event.x}` reads the event, `{header.x}` a
|
|
2098
|
+
* header and `{webhook.x}` the endpoint, and `{a || b}` falls back to `b` when `a` is empty. e.g.
|
|
2099
|
+
* `"{webhook.externalRef}:{event.data.object.customer}"`.
|
|
2100
|
+
*/
|
|
2101
|
+
key: ValidatedWebhookKey<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, TKey>;
|
|
2102
|
+
inbound: (event: NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>) => ChannelInbound;
|
|
2103
|
+
bind?: (event: NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>) => THandle | null;
|
|
2104
|
+
seed?: (event: NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, ctx: ChannelSeedCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>>) => Promise<ChannelSeedMessage[]> | ChannelSeedMessage[];
|
|
2105
|
+
outbound?: (reply: ChannelReply) => ChannelMessage | null;
|
|
2106
|
+
ack?: (event: NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, ctx: ChannelAckCtx) => ChannelMessage | null;
|
|
2107
|
+
send?: (message: ChannelMessage, ctx: ChannelSendCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>) => Promise<{
|
|
2108
|
+
ref?: string;
|
|
2109
|
+
}>;
|
|
2110
|
+
renderInteraction?: (pending: ChannelPendingToolCall[], ctx: ChannelInteractionCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>>) => ChannelMessage | null;
|
|
2111
|
+
onInteraction?: (event: NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>) => ChannelInteractionResolution | null;
|
|
2112
|
+
finalizeInteraction?: (event: NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, resolution: ChannelInteractionResolution) => Promise<void> | void;
|
|
2113
|
+
react?: (reaction: ChannelReaction, ctx: ChannelReactCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>>) => Promise<void>;
|
|
2114
|
+
reactions?: ChannelReactions<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>>;
|
|
2115
|
+
progress?: (event: ChannelProgressEvent, ctx: ChannelTurnCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>) => Promise<void> | void;
|
|
2116
|
+
surface?: (ctx: ChannelTurnCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>) => Record<string, unknown>;
|
|
2117
|
+
onControl?: (event: NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>) => ChannelControl | null;
|
|
2118
|
+
stream?: (ctx: ChannelStreamCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>) => ChannelReplyStream | null;
|
|
2119
|
+
endInterruptedStream?: (ref: string, ctx: ChannelTurnCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>) => Promise<void> | void;
|
|
2120
|
+
download?: (url: URL, ctx: {
|
|
2121
|
+
handle?: THandle;
|
|
2122
|
+
}) => Promise<ChannelDownloadedFile | null>;
|
|
2123
|
+
received?: (ctx: ChannelTurnCtx<InferWebhookEndpointEvent<TEndpoint>, THandle>) => Promise<void> | void;
|
|
2124
|
+
toAction?: (event: InferWebhookEndpointEvent<TEndpoint>) => unknown | null;
|
|
2125
|
+
lifecycle?: (state: ChannelLifecycleState, ctx: ChannelLifecycleCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>) => Promise<void> | void;
|
|
2126
|
+
cancelInteraction?: (cancelled: ChannelCancelledToolCall[], ctx: ChannelTurnCtx<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>) => Promise<void> | void;
|
|
2127
|
+
filter?: ValidateWebhookFilter<InferWebhookEndpointEvent<TEndpoint>, TFilter>;
|
|
2128
|
+
startOn?: ValidateWebhookFilter<InferWebhookEndpointEvent<TEndpoint>, TStartOn>;
|
|
2129
|
+
delivery?: "final" | "stream";
|
|
2130
|
+
/** What the channel shows when a turn fails: a line, or a function of the failure. Defaults to {@link CHANNEL_TURN_ERROR_MESSAGE}. */
|
|
2131
|
+
errorMessage?: ChannelErrorMessage<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>>;
|
|
2132
|
+
}): ChannelConnector<NarrowWebhookEvent<InferWebhookEndpointEvent<TEndpoint>, TFilter>, THandle>;
|
|
2133
|
+
export declare function resolveReactionChoice(choice: ChannelReactionChoice | undefined, event: unknown): Promise<string | undefined>;
|
|
2134
|
+
/**
|
|
2135
|
+
* Feed a connector's `progress()` from the UI message stream: a tool call once its input is available,
|
|
2136
|
+
* then its result or error. Calls are serialized so the surface sees them in order; a throw is logged.
|
|
2137
|
+
* `stop()` refuses further chunks and drains what is already queued, so a slow first post does not
|
|
2138
|
+
* lose the results behind it, and nothing new lands after the turn ended.
|
|
2139
|
+
*/
|
|
2140
|
+
declare function makeChannelProgressObserver(connector: AnyChannelConnector, wireEvent: {
|
|
2141
|
+
event: unknown;
|
|
2142
|
+
deliveryId: string;
|
|
2143
|
+
} | undefined, handle: unknown): ChannelStreamEditor;
|
|
2144
|
+
/**
|
|
2145
|
+
* Report a session's lifecycle to its connector in order, one call at a time, and re-send `working`
|
|
2146
|
+
* while a long turn runs. Every report bumps a sequence number and a refresh only fires while its
|
|
2147
|
+
* `working` is still the latest report, so a refresh can never land after the turn went idle.
|
|
2148
|
+
*/
|
|
2149
|
+
declare function makeChannelLifecycleReporter(): {
|
|
2150
|
+
report(connector: AnyChannelConnector | undefined, state: ChannelLifecycleState, ctx: ChannelLifecycleCtx): Promise<void>;
|
|
2151
|
+
dispose: () => void;
|
|
2152
|
+
};
|
|
2153
|
+
declare function makeChannelStreamEditor<TEvent>(connector: ChannelConnector<TEvent>, channelEvent: {
|
|
2154
|
+
event: unknown;
|
|
2155
|
+
deliveryId: string;
|
|
2156
|
+
}, ackRef: string, handle?: unknown): {
|
|
2157
|
+
observe(chunk: unknown): void;
|
|
2158
|
+
stop(): Promise<void>;
|
|
2159
|
+
};
|
|
2160
|
+
type ChannelStreamEditor = {
|
|
2161
|
+
observe(chunk: unknown): void;
|
|
2162
|
+
stop(): void | Promise<void>;
|
|
2163
|
+
};
|
|
2164
|
+
/**
|
|
2165
|
+
* Wrap the reply stream so it debounce-edits the channel message as it streams.
|
|
2166
|
+
* Both `flush` (the stream completed) and `cancel` (the stream was aborted or
|
|
2167
|
+
* cancelled downstream) stop the editor, so a pending debounce timer can never
|
|
2168
|
+
* fire an edit after the turn ended, onto a message the next turn already owns.
|
|
2169
|
+
*/
|
|
2170
|
+
/**
|
|
2171
|
+
* Feed every chunk of a stream to `editor`. By default the editor is stopped when the stream ends or
|
|
2172
|
+
* is cancelled (one stream per turn, the automatic pipe). With `stopOnEnd: false` the editor outlives
|
|
2173
|
+
* the stream, for a turn whose run() pipes several streams through `chat.pipe()`; the turn boundary
|
|
2174
|
+
* stops it.
|
|
2175
|
+
*/
|
|
2176
|
+
declare function makeChannelStreamTap(editor: ChannelStreamEditor, options?: {
|
|
2177
|
+
stopOnEnd?: boolean;
|
|
2178
|
+
}): TransformStream<unknown, unknown>;
|
|
2179
|
+
export { makeChannelStreamEditor as __makeChannelStreamEditorForTests, makeChannelStreamTap as __makeChannelStreamTapForTests, makeChannelProgressObserver as __makeChannelProgressObserverForTests, makeChannelLifecycleReporter as __makeChannelLifecycleReporterForTests, };
|
|
2180
|
+
/** Resolves once the post-turn channel egress for `chatId` has finished (immediately when none is running). */
|
|
2181
|
+
export declare function __waitForChannelEgressForTests(chatId: string): Promise<void>;
|
|
2182
|
+
type ChatActionType<TActionSchema extends TaskSchema | undefined, TW extends readonly AnyChatEvent[]> = [TActionSchema] extends [TaskSchema] ? inferSchemaOut<TActionSchema> | ChatEventActions<TW> : [TW] extends [readonly []] ? unknown : ChatEventActions<TW>;
|
|
2183
|
+
export type ChatAgentOptions<TIdentifier extends string, TClientDataSchema extends TaskSchema | undefined = undefined, TUIMessage extends UIMessage = UIMessage, TActionSchema extends TaskSchema | undefined = undefined, TTools extends ToolSet = ToolSet, TW extends readonly AnyChatEvent[] = [], TChannels extends readonly AnyChannelConnector[] = []> = Omit<TaskOptions<TIdentifier, ChatTaskWirePayload<TUIMessage, inferSchemaIn<TClientDataSchema>>, unknown>, "run" | "retry"> & {
|
|
1636
2184
|
/**
|
|
1637
2185
|
* Fallback machine preset to use when an attempt fails with an
|
|
1638
2186
|
* out-of-memory (OOM) error. Setting this enables a single OOM retry:
|
|
@@ -1677,6 +2225,31 @@ export type ChatAgentOptions<TIdentifier extends string, TClientDataSchema exten
|
|
|
1677
2225
|
* Ignored for sessions with no pin, and for sessions using `lockToVersion`.
|
|
1678
2226
|
*/
|
|
1679
2227
|
versionSkew?: ChatVersionSkewPolicy;
|
|
2228
|
+
/**
|
|
2229
|
+
* Controls which chat content the chat runtime records on its spans in the run trace.
|
|
2230
|
+
*
|
|
2231
|
+
* - `recordUserMessage` (default `true`) records the last user message as `chat.user_message`
|
|
2232
|
+
* and as the turn span's preview text, and messages sent mid-turn as `pending.messages`.
|
|
2233
|
+
* - `recordClientData` (default `true`) records the raw `clientData` sent by the frontend as
|
|
2234
|
+
* `chat.client_data`.
|
|
2235
|
+
*
|
|
2236
|
+
* Set either to `false` to keep that content out of telemetry. Content recorded by the AI SDK's
|
|
2237
|
+
* own spans is controlled separately, through `experimental_telemetry` on the model call.
|
|
2238
|
+
*
|
|
2239
|
+
* @example
|
|
2240
|
+
* ```ts
|
|
2241
|
+
* chat.agent({
|
|
2242
|
+
* id: "my-chat",
|
|
2243
|
+
* telemetry: { recordUserMessage: false, recordClientData: false },
|
|
2244
|
+
* run: async ({ messages, signal, streamText }) =>
|
|
2245
|
+
* streamText({ model, messages, abortSignal: signal }),
|
|
2246
|
+
* });
|
|
2247
|
+
* ```
|
|
2248
|
+
*/
|
|
2249
|
+
telemetry?: {
|
|
2250
|
+
recordUserMessage?: boolean;
|
|
2251
|
+
recordClientData?: boolean;
|
|
2252
|
+
};
|
|
1680
2253
|
/**
|
|
1681
2254
|
* Schema for validating `clientData` from the frontend.
|
|
1682
2255
|
* Accepts Zod, ArkType, Valibot, or any supported schema library.
|
|
@@ -1736,9 +2309,22 @@ export type ChatAgentOptions<TIdentifier extends string, TClientDataSchema exten
|
|
|
1736
2309
|
* action that returns nothing is a state edit only. Returning anything else
|
|
1737
2310
|
* is an error; a response can no longer be returned directly.
|
|
1738
2311
|
*/
|
|
1739
|
-
|
|
1740
|
-
|
|
1741
|
-
|
|
2312
|
+
/**
|
|
2313
|
+
* Inbound `chat.event(...)` descriptors this agent handles. Listing one subscribes this agent to the
|
|
2314
|
+
* descriptor's endpoint: each verified delivery goes to the session its `key` names and arrives at
|
|
2315
|
+
* `onAction` as a `{ type, event, source, headers, deliveryId, externalDeliveryId, endpoint }` envelope whose `type` is
|
|
2316
|
+
* the descriptor's `type`. The same descriptor listed on another agent is a second subscriber on the
|
|
2317
|
+
* same endpoint.
|
|
2318
|
+
*/
|
|
2319
|
+
events?: TW;
|
|
2320
|
+
/**
|
|
2321
|
+
* Inbound chat frontends (Slack, etc.) via `chat.channels.*`. Listing one subscribes this agent to
|
|
2322
|
+
* the connector's endpoint, routing verified events to a durable per-key session as turns: the
|
|
2323
|
+
* connector's `inbound()` maps the raw event to the turn's message, `run()` fires as normal, and the
|
|
2324
|
+
* reply streams back to the channel. Use the connector's `filter` to ignore events.
|
|
2325
|
+
*/
|
|
2326
|
+
channels?: TChannels;
|
|
2327
|
+
onAction?: (event: ActionEvent<ChatActionType<TActionSchema, TW>, inferSchemaOut<TClientDataSchema>, TUIMessage>) => Promise<void | ActionTurn> | void | ActionTurn;
|
|
1742
2328
|
/**
|
|
1743
2329
|
* The tools available to this agent.
|
|
1744
2330
|
*
|
|
@@ -1954,6 +2540,13 @@ export type ChatAgentOptions<TIdentifier extends string, TClientDataSchema exten
|
|
|
1954
2540
|
* },
|
|
1955
2541
|
* });
|
|
1956
2542
|
* ```
|
|
2543
|
+
*
|
|
2544
|
+
* Note: on a channel HITL resume turn (a button click that lands on a fresh
|
|
2545
|
+
* run whose accumulator doesn't yet hold the pending tool call), this hook is
|
|
2546
|
+
* called twice for the one delivery: once with `incomingMessages: []` to load
|
|
2547
|
+
* the chain and locate the pending tool call, then again with the synthesized
|
|
2548
|
+
* resolution message so it can be persisted. Keep the hook's read path
|
|
2549
|
+
* idempotent.
|
|
1957
2550
|
*/
|
|
1958
2551
|
hydrateMessages?: (event: HydrateMessagesEvent<inferSchemaOut<TClientDataSchema>, TUIMessage>) => TUIMessage[] | Promise<TUIMessage[]>;
|
|
1959
2552
|
/**
|
|
@@ -2341,7 +2934,7 @@ type ChatCustomAgentOptions<TIdentifier extends string, TClientDataSchema extend
|
|
|
2341
2934
|
run: TaskOptions<TIdentifier, ChatTaskWirePayload<TUIMessage, inferSchemaOut<TClientDataSchema>>, unknown>["run"];
|
|
2342
2935
|
};
|
|
2343
2936
|
declare function chatCustomAgent<TIdentifier extends string, TClientDataSchema extends TaskSchema | undefined = undefined, TUIMessage extends UIMessage = UIMessage>(options: ChatCustomAgentOptions<TIdentifier, TClientDataSchema, TUIMessage>): Task<TIdentifier, ChatTaskWirePayload<TUIMessage, inferSchemaIn<TClientDataSchema>>, unknown>;
|
|
2344
|
-
declare function chatAgent<TIdentifier extends string, TClientDataSchema extends TaskSchema | undefined = undefined, TUIMessage extends UIMessage = UIMessage, TActionSchema extends TaskSchema | undefined = undefined, TTools extends ToolSet = ToolSet>(options: ChatAgentOptions<TIdentifier, TClientDataSchema, TUIMessage, TActionSchema, TTools>): Task<TIdentifier, ChatTaskWirePayload<TUIMessage, inferSchemaIn<TClientDataSchema>>, unknown>;
|
|
2937
|
+
declare function chatAgent<TIdentifier extends string, TClientDataSchema extends TaskSchema | undefined = undefined, TUIMessage extends UIMessage = UIMessage, TActionSchema extends TaskSchema | undefined = undefined, TTools extends ToolSet = ToolSet, const TW extends readonly AnyChatEvent[] = [], const TChannels extends readonly AnyChannelConnector[] = []>(options: ChatAgentOptions<TIdentifier, TClientDataSchema, TUIMessage, TActionSchema, TTools, TW, TChannels>): Task<TIdentifier, ChatTaskWirePayload<TUIMessage, inferSchemaIn<TClientDataSchema>>, unknown>;
|
|
2345
2938
|
/**
|
|
2346
2939
|
* Optional config for {@link chat.withUIMessage}. `streamOptions` become default
|
|
2347
2940
|
* static `toUIMessageStream()` settings; inner `chat.agent({ uiMessageStreamOptions })`
|
|
@@ -2552,6 +3145,20 @@ declare function setIdleTimeoutInSeconds(seconds: number): void;
|
|
|
2552
3145
|
* ```
|
|
2553
3146
|
*/
|
|
2554
3147
|
declare function setUIMessageStreamOptions(options: ChatUIMessageStreamOptions<UIMessage>): void;
|
|
3148
|
+
/**
|
|
3149
|
+
* The channel surface of the current turn, from anywhere inside a `chat.agent` run, including a
|
|
3150
|
+
* tool's `execute`. Undefined on a browser turn or when the connector defines no reactions and no
|
|
3151
|
+
* `surface()`. Pass the connector's surface type to get its helpers typed:
|
|
3152
|
+
*
|
|
3153
|
+
* @example
|
|
3154
|
+
* ```ts
|
|
3155
|
+
* execute: async ({ steps }) => {
|
|
3156
|
+
* const linear = chat.surface<LinearRunSurface>();
|
|
3157
|
+
* if (linear) await linear.plan(steps);
|
|
3158
|
+
* }
|
|
3159
|
+
* ```
|
|
3160
|
+
*/
|
|
3161
|
+
declare function getChannelSurface<T extends ChannelRunSurface = ChannelRunSurface>(): T | undefined;
|
|
2555
3162
|
/**
|
|
2556
3163
|
* Check whether the user stopped generation during the current turn.
|
|
2557
3164
|
*
|
|
@@ -3407,6 +4014,13 @@ declare function createChatLoadTranscriptAction<TClientData = unknown>(storage:
|
|
|
3407
4014
|
export declare const chat: {
|
|
3408
4015
|
/** Create a chat agent. See {@link chatAgent}. */
|
|
3409
4016
|
agent: typeof chatAgent;
|
|
4017
|
+
/** Declare an inbound webhook event an agent claims via `chat.agent({ events })`. See {@link chatEvent}. */
|
|
4018
|
+
event: typeof chatEvent;
|
|
4019
|
+
/** Chat frontend connectors (Slack, etc.) an agent claims via `chat.agent({ channels })`. */
|
|
4020
|
+
channels: {
|
|
4021
|
+
/** A generic chat-frontend channel over any source, with your own egress. See {@link chatChannelCustom}. */
|
|
4022
|
+
custom: typeof chatChannelCustom;
|
|
4023
|
+
};
|
|
3410
4024
|
/** Create a custom agent with manual lifecycle control. See {@link chatCustomAgent}. */
|
|
3411
4025
|
customAgent: typeof chatCustomAgent;
|
|
3412
4026
|
/** Create a chat task with a fixed {@link UIMessage} subtype and optional default stream options. See {@link withUIMessage}. */
|
|
@@ -3425,6 +4039,8 @@ export declare const chat: {
|
|
|
3425
4039
|
local: typeof chatLocal;
|
|
3426
4040
|
/** Create a public access token for a chat task. See {@link createChatAccessToken}. */
|
|
3427
4041
|
createAccessToken: typeof createChatAccessToken;
|
|
4042
|
+
/** Mint a read-only token to WATCH a session by externalId (cross-surface). See {@link createChatWatchToken}. */
|
|
4043
|
+
createWatchToken: typeof createChatWatchToken;
|
|
3428
4044
|
/** Override the turn timeout at runtime (duration string). See {@link setTurnTimeout}. */
|
|
3429
4045
|
setTurnTimeout: typeof setTurnTimeout;
|
|
3430
4046
|
/** Override the turn timeout at runtime (seconds). See {@link setTurnTimeoutInSeconds}. */
|
|
@@ -3435,6 +4051,8 @@ export declare const chat: {
|
|
|
3435
4051
|
setUIMessageStreamOptions: typeof setUIMessageStreamOptions;
|
|
3436
4052
|
/** Check if the current turn was stopped by the user. See {@link isStopped}. */
|
|
3437
4053
|
isStopped: typeof isStopped;
|
|
4054
|
+
/** The current turn's channel surface (reactions plus connector helpers), also from inside a tool. See {@link getChannelSurface}. */
|
|
4055
|
+
surface: typeof getChannelSurface;
|
|
3438
4056
|
/** Request that the run exits after the current turn so the next message starts on the latest version. See {@link requestUpgrade}. */
|
|
3439
4057
|
requestUpgrade: typeof requestUpgrade;
|
|
3440
4058
|
/** Hand off a custom agent Session to a fresh run. See {@link endAndContinue}. */
|