@jini-ai/chat 0.3.11 → 0.5.0
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/CHANGELOG.md +126 -0
- package/README.md +152 -6
- package/dist/core/ag-ui/entry.d.ts +53 -0
- package/dist/core/ag-ui/entry.js +135 -0
- package/dist/core/agentic/chat-capabilities.d.ts +1 -1
- package/dist/core/agentic/index.d.ts +1 -1
- package/dist/core/agentic/index.js +1 -1
- package/dist/core/assistant-content.d.ts +6 -2
- package/dist/core/assistant-content.js +2 -2
- package/dist/core/compact-events.d.ts +3 -1
- package/dist/core/compact-events.js +1 -1
- package/dist/core/events.d.ts +1 -1
- package/dist/core/events.js +1 -1
- package/dist/core/index.d.ts +3 -3
- package/dist/core/index.js +3 -3
- package/dist/core/messages.d.ts +4 -2
- package/dist/core/messages.js +2 -2
- package/dist/core/partial-json.d.ts +6 -2
- package/dist/core/partial-json.js +3 -3
- package/dist/core/persistence/index.d.ts +1 -1
- package/dist/core/persistence/index.js +1 -1
- package/dist/core/persistence/ports.d.ts +2 -123
- package/dist/core/persistence/title.d.ts +3 -1
- package/dist/core/persistence/title.js +1 -1
- package/dist/core/question-form/format.d.ts +16 -7
- package/dist/core/question-form/format.js +3 -3
- package/dist/core/question-form/normalize.d.ts +7 -2
- package/dist/core/question-form/normalize.js +5 -5
- package/dist/core/question-form/scan.d.ts +18 -6
- package/dist/core/question-form/scan.js +14 -14
- package/dist/core/run-activity.d.ts +16 -4
- package/dist/core/run-activity.js +11 -11
- package/dist/core/run-events/entry.d.ts +121 -0
- package/dist/core/run-events/entry.js +290 -0
- package/dist/core/todos.d.ts +20 -8
- package/dist/core/todos.js +11 -11
- package/dist/core/tool-events.d.ts +3 -1
- package/dist/core/tool-events.js +1 -1
- package/dist/core/tool-output.d.ts +3 -1
- package/dist/core/tool-output.js +1 -1
- package/dist/core/tools.d.ts +14 -3
- package/dist/core/tools.js +3 -3
- package/dist/core/transcript.d.ts +13 -5
- package/dist/core/transcript.js +5 -5
- package/dist/core/util/manifest.d.ts +9 -3
- package/dist/core/util/manifest.js +3 -3
- package/dist/core/util/markdown-context.d.ts +11 -3
- package/dist/core/util/markdown-context.js +3 -3
- package/dist/core/util/markup-attributes.d.ts +3 -1
- package/dist/core/util/markup-attributes.js +1 -1
- package/dist/core/util/parser.d.ts +9 -5
- package/dist/core/util/parser.js +13 -13
- package/dist/core/util/recover.d.ts +6 -2
- package/dist/core/util/recover.js +6 -6
- package/dist/core/util/strip.d.ts +19 -5
- package/dist/core/util/strip.js +17 -17
- package/dist/core/util/validate.d.ts +3 -1
- package/dist/core/util/validate.js +1 -1
- package/dist/embed-widget/browser/page-actions.d.ts +121 -0
- package/dist/embed-widget/browser/page-actions.js +113 -0
- package/dist/embed-widget/browser/session-store.d.ts +44 -0
- package/dist/embed-widget/browser/session-store.js +103 -0
- package/dist/embed-widget/react/embed.d.ts +45 -0
- package/dist/embed-widget/react/embed.js +87 -0
- package/dist/embed-widget/react/header.d.ts +21 -0
- package/dist/embed-widget/react/header.js +18 -0
- package/dist/embed-widget/transports/fetch-sse.d.ts +75 -0
- package/dist/embed-widget/transports/fetch-sse.js +175 -0
- package/dist/react/agent-bridge/frontend-session-bridge.d.ts +15 -3
- package/dist/react/agent-bridge/frontend-session-bridge.js +13 -6
- package/dist/react/artifact-types.d.ts +3 -3
- package/dist/react/artifact-types.js +3 -3
- package/dist/react/components/A2uiSurfaceCard.js +34 -13
- package/dist/react/components/AttachmentPreviewModal.hooks.d.ts +7 -2
- package/dist/react/components/AttachmentPreviewModal.hooks.js +5 -5
- package/dist/react/components/AttachmentPreviewModal.js +2 -2
- package/dist/react/components/AttachmentTray.d.ts +3 -1
- package/dist/react/components/AttachmentTray.js +2 -2
- package/dist/react/components/ChatFab.js +1 -1
- package/dist/react/components/Composer.js +9 -9
- package/dist/react/components/ConversationList.js +1 -1
- package/dist/react/components/McpUiSurfaceCard.d.ts +4 -2
- package/dist/react/components/McpUiSurfaceCard.js +5 -5
- package/dist/react/components/MessageList.js +1 -1
- package/dist/react/components/MessageRow.js +9 -9
- package/dist/react/components/QuestionForm.js +5 -5
- package/dist/react/components/ToolCard.js +9 -9
- package/dist/react/components/composer-discovery.d.ts +29 -8
- package/dist/react/components/composer-discovery.js +10 -10
- package/dist/react/ext-event-renderer-registry.d.ts +15 -5
- package/dist/react/ext-event-renderer-registry.js +4 -4
- package/dist/react/features/chat-pane/components/AgentRuntimePicker.d.ts +3 -1
- package/dist/react/features/chat-pane/components/AgentRuntimePicker.js +3 -3
- package/dist/react/features/chat-pane/components/ChatPane.js +43 -43
- package/dist/react/features/chat-pane/create-daemon-attachment-uploader.d.ts +4 -1
- package/dist/react/features/chat-pane/create-daemon-attachment-uploader.js +5 -35
- package/dist/react/features/chat-pane/create-mcp-ui-tool-caller.d.ts +5 -2
- package/dist/react/features/chat-pane/create-mcp-ui-tool-caller.js +1 -1
- package/dist/react/features/chat-pane/hooks/useAgentRuntimePicker.hooks.d.ts +38 -10
- package/dist/react/features/chat-pane/hooks/useAgentRuntimePicker.hooks.js +15 -15
- package/dist/react/features/chat-pane/hooks/useChatPane.hooks.js +31 -31
- package/dist/react/features/chat-pane/hooks/useChatPaneAgentControl.hooks.d.ts +3 -1
- package/dist/react/features/chat-pane/hooks/useChatPaneAgentControl.hooks.js +3 -3
- package/dist/react/features/chat-pane/hooks/useChatPaneComposerPlaceholder.hooks.d.ts +4 -1
- package/dist/react/features/chat-pane/hooks/useChatPaneComposerPlaceholder.hooks.js +1 -1
- package/dist/react/features/chat-pane/hooks/useChatPaneRuntimeInventory.hooks.js +30 -30
- package/dist/react/features/chat-pane/hooks/useChatPaneWorkingDirectory.hooks.js +57 -57
- package/dist/react/features/chat-pane/rules.d.ts +13 -4
- package/dist/react/features/chat-pane/rules.js +5 -5
- package/dist/react/features/chat-pane/types.d.ts +1 -1
- package/dist/react/hooks/attachment-preview-cache.d.ts +7 -2
- package/dist/react/hooks/attachment-preview-cache.js +2 -2
- package/dist/react/hooks/composer-draft-cache.d.ts +17 -5
- package/dist/react/hooks/composer-draft-cache.js +6 -6
- package/dist/react/hooks/useArtifactStream.d.ts +5 -1
- package/dist/react/hooks/useArtifactStream.js +3 -3
- package/dist/react/hooks/useChatFabDrag.d.ts +9 -4
- package/dist/react/hooks/useChatFabDrag.js +4 -4
- package/dist/react/hooks/useComposer.js +8 -8
- package/dist/react/hooks/useConversation.js +56 -4
- package/dist/react/hooks/useExtEventGroups.d.ts +5 -1
- package/dist/react/hooks/useExtEventGroups.js +1 -1
- package/dist/react/hooks/useLatestOperation.d.ts +8 -3
- package/dist/react/hooks/useLatestOperation.js +4 -4
- package/dist/react/hooks/usePinnedTodos.d.ts +3 -1
- package/dist/react/hooks/usePinnedTodos.js +3 -3
- package/dist/react/hooks/useQuestionForms.d.ts +7 -2
- package/dist/react/hooks/useQuestionForms.js +7 -7
- package/dist/react/hooks/useRunActivity.d.ts +6 -1
- package/dist/react/hooks/useRunActivity.js +3 -3
- package/dist/react/hooks/useRunStream.d.ts +3 -1
- package/dist/react/hooks/useRunStream.js +1 -1
- package/dist/react/hooks/useToolTimeline.d.ts +3 -1
- package/dist/react/hooks/useToolTimeline.js +3 -3
- package/dist/react/index.d.ts +4 -4
- package/dist/react/index.js +6 -6
- package/dist/react/message-blocks.d.ts +10 -4
- package/dist/react/message-blocks.js +2 -2
- package/dist/react/styles/reference.css +3 -3
- package/dist/react/tool-renderer-registry.d.ts +8 -3
- package/dist/react/tool-renderer-registry.js +3 -3
- package/dist/react/util/defined-props.d.ts +3 -1
- package/dist/react/util/defined-props.js +1 -1
- package/dist/server/run-finalizer/entry.d.ts +47 -0
- package/dist/server/run-finalizer/entry.js +156 -0
- package/dist/server/run-finalizer/ports.d.ts +52 -0
- package/dist/store/contracts/index.d.ts +5 -0
- package/dist/store/contracts/index.js +5 -0
- package/dist/store/errors.d.ts +12 -0
- package/dist/store/errors.js +18 -0
- package/dist/store/index.d.ts +4 -0
- package/dist/store/index.js +2 -0
- package/dist/store/legacy/index.d.ts +3 -0
- package/dist/store/legacy/index.js +2 -0
- package/dist/store/legacy/sqlite/conversations.d.ts +129 -0
- package/dist/store/legacy/sqlite/conversations.js +274 -0
- package/dist/store/legacy/sqlite/index.d.ts +6 -0
- package/dist/store/legacy/sqlite/index.js +5 -0
- package/dist/store/legacy/sqlite/messages.d.ts +156 -0
- package/dist/store/legacy/sqlite/messages.js +246 -0
- package/dist/store/legacy/sqlite/schema.d.ts +3 -0
- package/dist/store/legacy/sqlite/schema.js +40 -0
- package/dist/store/pglite/index.d.ts +21 -0
- package/dist/store/pglite/index.js +17 -0
- package/dist/store/ports.d.ts +121 -0
- package/dist/store/ports.js +2 -0
- package/dist/store/postgres/index.d.ts +21 -0
- package/dist/store/postgres/index.js +17 -0
- package/dist/store/sql/boundary.d.ts +28 -0
- package/dist/store/sql/boundary.js +32 -0
- package/dist/store/sql/cursor.d.ts +24 -0
- package/dist/store/sql/cursor.js +49 -0
- package/dist/store/sql/maintenance.d.ts +9 -0
- package/dist/store/sql/maintenance.js +16 -0
- package/dist/store/sql/store.d.ts +22 -0
- package/dist/store/sql/store.js +340 -0
- package/dist/store/sql/tables.d.ts +34 -0
- package/dist/store/sql/tables.js +2 -0
- package/dist/store/sqlite/index.d.ts +36 -0
- package/dist/store/sqlite/index.js +29 -0
- package/dist/store/sqlite/schema.d.ts +49 -0
- package/dist/store/sqlite/schema.js +80 -0
- package/package.json +211 -14
- package/dist/react/features/model-picker/components/CredentialStatusBadge.d.ts +0 -7
- package/dist/react/features/model-picker/components/CredentialStatusBadge.js +0 -20
- package/dist/react/features/model-picker/components/ModelPicker.d.ts +0 -9
- package/dist/react/features/model-picker/components/ModelPicker.js +0 -34
- package/dist/react/features/model-picker/constants.d.ts +0 -6
- package/dist/react/features/model-picker/constants.js +0 -9
- package/dist/react/features/model-picker/dependencies.d.ts +0 -11
- package/dist/react/features/model-picker/dependencies.js +0 -10
- package/dist/react/features/model-picker/hooks/useModelPicker.hooks.d.ts +0 -27
- package/dist/react/features/model-picker/hooks/useModelPicker.hooks.js +0 -62
- package/dist/react/features/model-picker/index.d.ts +0 -32
- package/dist/react/features/model-picker/index.js +0 -29
- package/dist/react/features/model-picker/ports.d.ts +0 -11
- package/dist/react/features/model-picker/rules.d.ts +0 -26
- package/dist/react/features/model-picker/rules.js +0 -84
- package/dist/react/features/model-picker/types.d.ts +0 -38
- package/dist/react/features/model-picker/types.js +0 -2
- package/dist/react/poc-mcp-ui-official/PocMcpUiCard.d.ts +0 -9
- package/dist/react/poc-mcp-ui-official/PocMcpUiCard.js +0 -29
- package/dist/react/poc-mcp-ui-official/create-poc-resource.d.ts +0 -30
- package/dist/react/poc-mcp-ui-official/create-poc-resource.js +0 -44
- /package/dist/{react/features/model-picker → server/run-finalizer}/ports.js +0 -0
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
/** Framework-free daemon frame reduction, shared by live and saved chat turns.
|
|
2
|
+
* Preserve named frame vocabulary, terminal classifications, error-before-success precedence,
|
|
3
|
+
* compaction and paragraph boundaries so live and persisted turns agree. Notice strings, custom
|
|
4
|
+
* event names and excluded run-ID prefixes are explicit host inputs, never product wire defaults.
|
|
5
|
+
* Authenticated routing, ownership, boot repair and storage transactions remain host responsibilities. */
|
|
6
|
+
import type { AgentEvent } from "../events.js";
|
|
7
|
+
import type { ChatRunStatus } from "../messages.js";
|
|
8
|
+
export interface RunAgentPayload {
|
|
9
|
+
readonly type: string;
|
|
10
|
+
readonly [key: string]: unknown;
|
|
11
|
+
}
|
|
12
|
+
export interface RunProtocolEventWire {
|
|
13
|
+
readonly runId: string;
|
|
14
|
+
readonly kind: "start" | "agent" | "stdout" | "stderr" | "error" | "end";
|
|
15
|
+
readonly payload: unknown;
|
|
16
|
+
}
|
|
17
|
+
/** Display a wire scalar or JSON value using the existing empty-null convention. */
|
|
18
|
+
export declare function asString({ value }: {
|
|
19
|
+
value: unknown;
|
|
20
|
+
}): string;
|
|
21
|
+
/** Keep only numeric usage fields; omit absent fields without changing JSON output. */
|
|
22
|
+
export declare function parseUsageEvent({ payload }: {
|
|
23
|
+
payload: RunAgentPayload;
|
|
24
|
+
}): AgentEvent;
|
|
25
|
+
/** Reduce one daemon payload; preserve UI envelopes and drop duplicate input fragments. */
|
|
26
|
+
export declare function translateRunAgentPayload({ payload }: {
|
|
27
|
+
payload: RunAgentPayload;
|
|
28
|
+
}): AgentEvent | null;
|
|
29
|
+
/** Host-supplied status messages; no host branding or log path defaults. */
|
|
30
|
+
export interface RunNotices {
|
|
31
|
+
readonly toolStepLimit: Extract<AgentEvent, {
|
|
32
|
+
kind: "status";
|
|
33
|
+
}>;
|
|
34
|
+
readonly interrupted: Extract<AgentEvent, {
|
|
35
|
+
kind: "status";
|
|
36
|
+
}>;
|
|
37
|
+
readonly neverStarted: Extract<AgentEvent, {
|
|
38
|
+
kind: "status";
|
|
39
|
+
}>;
|
|
40
|
+
readonly canceledLabel: string;
|
|
41
|
+
readonly failedLabel: string;
|
|
42
|
+
readonly terminalDetail: (args: {
|
|
43
|
+
outcome: TerminalOutcome;
|
|
44
|
+
}) => string;
|
|
45
|
+
}
|
|
46
|
+
/** A host notice for a run that used its tool-step budget. */
|
|
47
|
+
export declare function terminalReasonNotice({ reason, notice }: {
|
|
48
|
+
reason: string;
|
|
49
|
+
notice: Extract<AgentEvent, {
|
|
50
|
+
kind: "status";
|
|
51
|
+
}>;
|
|
52
|
+
}): AgentEvent | null;
|
|
53
|
+
export interface TerminalOutcome {
|
|
54
|
+
readonly status: "failed" | "canceled";
|
|
55
|
+
readonly code: string;
|
|
56
|
+
readonly signal: string;
|
|
57
|
+
readonly resumable: string;
|
|
58
|
+
}
|
|
59
|
+
/** Read non-successful daemon classification without throwing on malformed frames. */
|
|
60
|
+
export declare function readTerminalOutcome({ raw }: {
|
|
61
|
+
raw: string | undefined;
|
|
62
|
+
}): TerminalOutcome | null;
|
|
63
|
+
/** A visible terminal classification rendered with host-supplied copy. */
|
|
64
|
+
export declare function terminalOutcomeNotice({ raw, notices }: {
|
|
65
|
+
raw: string | undefined;
|
|
66
|
+
notices: RunNotices;
|
|
67
|
+
}): AgentEvent | null;
|
|
68
|
+
/** Report a failed run; operator cancellation is not a failure. */
|
|
69
|
+
export declare function terminalFailureError({ raw }: {
|
|
70
|
+
raw: string | undefined;
|
|
71
|
+
}): Error | null;
|
|
72
|
+
/** Read a wrapped daemon or bare provider terminal reason, failing soft. */
|
|
73
|
+
export declare function readTerminalReason({ raw, wrapped }: {
|
|
74
|
+
raw: string | undefined;
|
|
75
|
+
wrapped: boolean;
|
|
76
|
+
}): string;
|
|
77
|
+
/** Parse the existing named SSE framing; bare keepalive frames return null. */
|
|
78
|
+
export declare function parseFrame({ rawFrame }: {
|
|
79
|
+
rawFrame: string;
|
|
80
|
+
}): {
|
|
81
|
+
event: string;
|
|
82
|
+
data: string;
|
|
83
|
+
} | null;
|
|
84
|
+
/** Decode the existing named SSE framing; cancellation always releases its reader. */
|
|
85
|
+
export declare function readSseFrames({ body }: {
|
|
86
|
+
body: ReadableStream<Uint8Array>;
|
|
87
|
+
}): AsyncGenerator<{
|
|
88
|
+
event: string;
|
|
89
|
+
data: string;
|
|
90
|
+
}>;
|
|
91
|
+
/** Identify runs held by the daemon using the host's excluded ID prefixes. */
|
|
92
|
+
export declare function isDaemonRunId({ runId, excludedPrefixes }: {
|
|
93
|
+
runId: string;
|
|
94
|
+
excludedPrefixes: readonly string[];
|
|
95
|
+
}): boolean;
|
|
96
|
+
/** Copy the host's interruption notice into a saved turn. */
|
|
97
|
+
export declare function runInterruptedNotice({ notice }: {
|
|
98
|
+
notice: Extract<AgentEvent, {
|
|
99
|
+
kind: "status";
|
|
100
|
+
}>;
|
|
101
|
+
}): AgentEvent;
|
|
102
|
+
/** Use the same paragraph-boundary rule as a live chat turn. */
|
|
103
|
+
export declare function runContentFromEvents({ events }: {
|
|
104
|
+
events: readonly AgentEvent[];
|
|
105
|
+
}): string;
|
|
106
|
+
/** Compact adjacent text/thinking deltas for durable storage. */
|
|
107
|
+
export declare function runEventsForSave({ events }: {
|
|
108
|
+
events: readonly AgentEvent[];
|
|
109
|
+
}): AgentEvent[];
|
|
110
|
+
export interface RunFrameOutcome {
|
|
111
|
+
readonly events: AgentEvent[];
|
|
112
|
+
readonly error?: Error;
|
|
113
|
+
readonly terminal?: Extract<ChatRunStatus, "succeeded" | "failed" | "canceled">;
|
|
114
|
+
}
|
|
115
|
+
/** Fold one named daemon frame into events, a failure and an optional terminal status. */
|
|
116
|
+
export declare function translateRunFrame({ kind, raw, notices }: {
|
|
117
|
+
kind: string;
|
|
118
|
+
raw: string | undefined;
|
|
119
|
+
notices: RunNotices;
|
|
120
|
+
}): RunFrameOutcome;
|
|
121
|
+
//# sourceMappingURL=entry.d.ts.map
|
|
@@ -0,0 +1,290 @@
|
|
|
1
|
+
/** Framework-free daemon frame reduction, shared by live and saved chat turns.
|
|
2
|
+
* Preserve named frame vocabulary, terminal classifications, error-before-success precedence,
|
|
3
|
+
* compaction and paragraph boundaries so live and persisted turns agree. Notice strings, custom
|
|
4
|
+
* event names and excluded run-ID prefixes are explicit host inputs, never product wire defaults.
|
|
5
|
+
* Authenticated routing, ownership, boot repair and storage transactions remain host responsibilities. */
|
|
6
|
+
import { assistantContentFromEvents } from "../assistant-content.js";
|
|
7
|
+
import { mergeAdjacentTextEvents } from "../compact-events.js";
|
|
8
|
+
function wireString(v) {
|
|
9
|
+
return typeof v === "string" ? v : v == null ? "" : JSON.stringify(v);
|
|
10
|
+
}
|
|
11
|
+
/** Display a wire scalar or JSON value using the existing empty-null convention. */
|
|
12
|
+
export function asString({ value }) {
|
|
13
|
+
return wireString(value);
|
|
14
|
+
}
|
|
15
|
+
/** Keep only numeric usage fields; omit absent fields without changing JSON output. */
|
|
16
|
+
export function parseUsageEvent({ payload }) {
|
|
17
|
+
const usage = (payload.usage ?? {});
|
|
18
|
+
return {
|
|
19
|
+
kind: "usage",
|
|
20
|
+
...(typeof usage.input_tokens === "number" ? { inputTokens: usage.input_tokens } : {}),
|
|
21
|
+
...(typeof usage.output_tokens === "number" ? { outputTokens: usage.output_tokens } : {}),
|
|
22
|
+
...(typeof payload.costUsd === "number" ? { costUsd: payload.costUsd } : {}),
|
|
23
|
+
...(typeof payload.durationMs === "number" ? { durationMs: payload.durationMs } : {}),
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
/** Reduce one daemon payload; preserve UI envelopes and drop duplicate input fragments. */
|
|
27
|
+
export function translateRunAgentPayload({ payload }) {
|
|
28
|
+
switch (payload.type) {
|
|
29
|
+
case "status":
|
|
30
|
+
return { kind: "status", label: wireString(payload.label), ...(payload.detail ? { detail: wireString(payload.detail) } : {}) };
|
|
31
|
+
case "text_delta":
|
|
32
|
+
return { kind: "text", text: wireString(payload.delta) };
|
|
33
|
+
case "thinking_delta":
|
|
34
|
+
return { kind: "thinking", text: wireString(payload.delta) };
|
|
35
|
+
case "tool_use":
|
|
36
|
+
return { kind: "tool_use", id: wireString(payload.id), name: wireString(payload.name), input: payload.input };
|
|
37
|
+
case "tool_result":
|
|
38
|
+
return {
|
|
39
|
+
kind: "tool_result",
|
|
40
|
+
toolUseId: wireString(payload.toolUseId),
|
|
41
|
+
content: wireString(payload.content),
|
|
42
|
+
isError: Boolean(payload.isError),
|
|
43
|
+
...(Array.isArray(payload.media) ? { media: payload.media } : {}),
|
|
44
|
+
};
|
|
45
|
+
case "usage":
|
|
46
|
+
return parseUsageEvent({ payload });
|
|
47
|
+
case "raw":
|
|
48
|
+
return { kind: "raw", line: wireString(payload.line) };
|
|
49
|
+
case "mcp-ui":
|
|
50
|
+
return { kind: "ext", name: "mcp-ui", data: payload.resource };
|
|
51
|
+
case "a2ui":
|
|
52
|
+
return { kind: "ext", name: "a2ui", data: payload.message };
|
|
53
|
+
case "thinking_start":
|
|
54
|
+
return null;
|
|
55
|
+
case "tool_input_delta":
|
|
56
|
+
return null;
|
|
57
|
+
default:
|
|
58
|
+
return { kind: "ext", name: payload.type, data: payload };
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
/** A host notice for a run that used its tool-step budget. */
|
|
62
|
+
export function terminalReasonNotice({ reason, notice }) {
|
|
63
|
+
return reason === "max_tool_turns" ? { ...notice } : null;
|
|
64
|
+
}
|
|
65
|
+
function neverStarted(outcome) {
|
|
66
|
+
return outcome.status === "failed" && outcome.code === "none" && outcome.signal === "none" && outcome.resumable === "no";
|
|
67
|
+
}
|
|
68
|
+
/** Read non-successful daemon classification without throwing on malformed frames. */
|
|
69
|
+
export function readTerminalOutcome({ raw }) {
|
|
70
|
+
if (!raw)
|
|
71
|
+
return null;
|
|
72
|
+
let payload;
|
|
73
|
+
try {
|
|
74
|
+
const frame = JSON.parse(raw);
|
|
75
|
+
if (!isRecord(frame) || !isRecord(frame.payload))
|
|
76
|
+
return null;
|
|
77
|
+
payload = frame.payload;
|
|
78
|
+
}
|
|
79
|
+
catch {
|
|
80
|
+
return null;
|
|
81
|
+
}
|
|
82
|
+
const status = payload.status;
|
|
83
|
+
if (status !== "failed" && status !== "canceled")
|
|
84
|
+
return null;
|
|
85
|
+
return {
|
|
86
|
+
status,
|
|
87
|
+
code: typeof payload.code === "number" ? String(payload.code) : "none",
|
|
88
|
+
signal: typeof payload.signal === "string" ? payload.signal : "none",
|
|
89
|
+
resumable: payload.resumable === true ? "yes" : "no",
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
/** A visible terminal classification rendered with host-supplied copy. */
|
|
93
|
+
export function terminalOutcomeNotice({ raw, notices }) {
|
|
94
|
+
const outcome = readTerminalOutcome({ raw });
|
|
95
|
+
if (!outcome)
|
|
96
|
+
return null;
|
|
97
|
+
if (neverStarted(outcome))
|
|
98
|
+
return { ...notices.neverStarted };
|
|
99
|
+
return { kind: "status", label: outcome.status === "canceled" ? notices.canceledLabel : notices.failedLabel,
|
|
100
|
+
detail: notices.terminalDetail({ outcome }) };
|
|
101
|
+
}
|
|
102
|
+
/** Report a failed run; operator cancellation is not a failure. */
|
|
103
|
+
export function terminalFailureError({ raw }) {
|
|
104
|
+
const outcome = readTerminalOutcome({ raw });
|
|
105
|
+
if (!outcome || outcome.status !== "failed")
|
|
106
|
+
return null;
|
|
107
|
+
if (neverStarted(outcome))
|
|
108
|
+
return new Error("The run failed before the agent started.");
|
|
109
|
+
return new Error(`The agent process exited without answering (exit code ${outcome.code}, signal ${outcome.signal}, resumable ${outcome.resumable}).`);
|
|
110
|
+
}
|
|
111
|
+
/** Read a wrapped daemon or bare provider terminal reason, failing soft. */
|
|
112
|
+
export function readTerminalReason({ raw, wrapped }) {
|
|
113
|
+
if (!raw)
|
|
114
|
+
return "";
|
|
115
|
+
try {
|
|
116
|
+
const parsed = JSON.parse(raw);
|
|
117
|
+
const source = wrapped ? (parsed.payload ?? {}) : parsed;
|
|
118
|
+
return wireString(source.reason);
|
|
119
|
+
}
|
|
120
|
+
catch {
|
|
121
|
+
return "";
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
/** Parse the existing named SSE framing; bare keepalive frames return null. */
|
|
125
|
+
export function parseFrame({ rawFrame }) {
|
|
126
|
+
let event = "message";
|
|
127
|
+
const dataLines = [];
|
|
128
|
+
for (const line of rawFrame.split("\n")) {
|
|
129
|
+
if (line.startsWith("event:"))
|
|
130
|
+
event = line.slice(6).trim();
|
|
131
|
+
else if (line.startsWith("data:"))
|
|
132
|
+
dataLines.push(line.slice(5).trim());
|
|
133
|
+
}
|
|
134
|
+
return dataLines.length > 0 ? { event, data: dataLines.join("\n") } : null;
|
|
135
|
+
}
|
|
136
|
+
/** Decode the existing named SSE framing; cancellation always releases its reader. */
|
|
137
|
+
export async function* readSseFrames({ body }) {
|
|
138
|
+
const reader = body.getReader();
|
|
139
|
+
const decoder = new TextDecoder();
|
|
140
|
+
let buffer = "";
|
|
141
|
+
let ended = false;
|
|
142
|
+
try {
|
|
143
|
+
for (;;) {
|
|
144
|
+
const { done, value } = await reader.read();
|
|
145
|
+
if (done) {
|
|
146
|
+
ended = true;
|
|
147
|
+
break;
|
|
148
|
+
}
|
|
149
|
+
buffer += decoder.decode(value, { stream: true });
|
|
150
|
+
let boundary = buffer.indexOf("\n\n");
|
|
151
|
+
while (boundary !== -1) {
|
|
152
|
+
const rawFrame = buffer.slice(0, boundary);
|
|
153
|
+
buffer = buffer.slice(boundary + 2);
|
|
154
|
+
const frame = parseFrame({ rawFrame });
|
|
155
|
+
if (frame)
|
|
156
|
+
yield frame;
|
|
157
|
+
boundary = buffer.indexOf("\n\n");
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
finally {
|
|
162
|
+
if (!ended)
|
|
163
|
+
await reader.cancel().catch(() => undefined);
|
|
164
|
+
reader.releaseLock();
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
/** Identify runs held by the daemon using the host's excluded ID prefixes. */
|
|
168
|
+
export function isDaemonRunId({ runId, excludedPrefixes }) {
|
|
169
|
+
return runId.length > 0 && !excludedPrefixes.some(prefix => runId.startsWith(prefix));
|
|
170
|
+
}
|
|
171
|
+
/** Copy the host's interruption notice into a saved turn. */
|
|
172
|
+
export function runInterruptedNotice({ notice }) {
|
|
173
|
+
return { ...notice };
|
|
174
|
+
}
|
|
175
|
+
/** Use the same paragraph-boundary rule as a live chat turn. */
|
|
176
|
+
export function runContentFromEvents({ events }) {
|
|
177
|
+
return assistantContentFromEvents({ events });
|
|
178
|
+
}
|
|
179
|
+
/** Compact adjacent text/thinking deltas for durable storage. */
|
|
180
|
+
export function runEventsForSave({ events }) {
|
|
181
|
+
return mergeAdjacentTextEvents({ events });
|
|
182
|
+
}
|
|
183
|
+
function parseWire(raw) {
|
|
184
|
+
if (!raw)
|
|
185
|
+
return null;
|
|
186
|
+
try {
|
|
187
|
+
const parsed = JSON.parse(raw);
|
|
188
|
+
return isRecord(parsed) ? parsed : null;
|
|
189
|
+
}
|
|
190
|
+
catch {
|
|
191
|
+
return null;
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
function parseJsonLine(line) {
|
|
195
|
+
if (!line.startsWith("{"))
|
|
196
|
+
return null;
|
|
197
|
+
try {
|
|
198
|
+
const value = JSON.parse(line);
|
|
199
|
+
return typeof value === "object" && value !== null ? value : null;
|
|
200
|
+
}
|
|
201
|
+
catch {
|
|
202
|
+
return null;
|
|
203
|
+
}
|
|
204
|
+
}
|
|
205
|
+
function numberOf(value) {
|
|
206
|
+
return typeof value === "number" && Number.isFinite(value) ? value : undefined;
|
|
207
|
+
}
|
|
208
|
+
function retryData(line) {
|
|
209
|
+
const attempt = numberOf(line.attempt);
|
|
210
|
+
const maxAttempts = numberOf(line.max_retries);
|
|
211
|
+
return { ...(attempt !== undefined ? { attempt } : {}), ...(maxAttempts !== undefined ? { maxAttempts } : {}), service: "Claude" };
|
|
212
|
+
}
|
|
213
|
+
function heartbeatStatus(line) {
|
|
214
|
+
if (line.type === "tool_progress") {
|
|
215
|
+
const elapsedSeconds = numberOf(line.elapsed_time_seconds);
|
|
216
|
+
return { kind: "status", code: "tool_progress", label: "tool_progress", ...(elapsedSeconds !== undefined ? { data: { elapsedSeconds } } : {}) };
|
|
217
|
+
}
|
|
218
|
+
if (line.type !== "system")
|
|
219
|
+
return null;
|
|
220
|
+
if (line.subtype === "api_retry") {
|
|
221
|
+
const detail = [numberOf(line.error_status), typeof line.error === "string" ? line.error : undefined].filter((p) => p !== undefined).join(" ");
|
|
222
|
+
return { kind: "status", code: "api_retry", label: "api_retry", ...(detail ? { detail } : {}), data: retryData(line) };
|
|
223
|
+
}
|
|
224
|
+
if (line.subtype === "thinking_tokens")
|
|
225
|
+
return { kind: "status", code: "thinking", label: "thinking" };
|
|
226
|
+
return null;
|
|
227
|
+
}
|
|
228
|
+
const ECHO_LINE = /^\{"type":"(?:stream_event|assistant|user)"/;
|
|
229
|
+
function chunkEvent(raw) {
|
|
230
|
+
const frame = parseWire(raw);
|
|
231
|
+
if (!frame)
|
|
232
|
+
return [];
|
|
233
|
+
const chunk = wireString(frame.payload?.chunk);
|
|
234
|
+
const statuses = [];
|
|
235
|
+
let kept = "";
|
|
236
|
+
let droppedAny = false;
|
|
237
|
+
for (const piece of chunk.split(/(?<=\n)/)) {
|
|
238
|
+
if (ECHO_LINE.test(piece.trimStart())) {
|
|
239
|
+
droppedAny = true;
|
|
240
|
+
continue;
|
|
241
|
+
}
|
|
242
|
+
const line = parseJsonLine(piece.trim());
|
|
243
|
+
const status = line ? heartbeatStatus(line) : null;
|
|
244
|
+
if (status)
|
|
245
|
+
statuses.push(status);
|
|
246
|
+
kept += piece;
|
|
247
|
+
}
|
|
248
|
+
if (!droppedAny)
|
|
249
|
+
kept = chunk;
|
|
250
|
+
return kept.length > 0 ? [{ kind: "raw", line: kept }, ...statuses] : statuses;
|
|
251
|
+
}
|
|
252
|
+
function endOutcome(raw, notices) {
|
|
253
|
+
const events = [];
|
|
254
|
+
const reasonNotice = terminalReasonNotice({ reason: readTerminalReason({ raw, wrapped: true }), notice: notices.toolStepLimit });
|
|
255
|
+
if (reasonNotice)
|
|
256
|
+
events.push(reasonNotice);
|
|
257
|
+
const outcomeNotice = terminalOutcomeNotice({ raw, notices });
|
|
258
|
+
if (outcomeNotice)
|
|
259
|
+
events.push(outcomeNotice);
|
|
260
|
+
const error = terminalFailureError({ raw });
|
|
261
|
+
const outcome = readTerminalOutcome({ raw });
|
|
262
|
+
const terminal = outcome?.status ?? "succeeded";
|
|
263
|
+
return error ? { events, error, terminal } : { events, terminal };
|
|
264
|
+
}
|
|
265
|
+
/** Fold one named daemon frame into events, a failure and an optional terminal status. */
|
|
266
|
+
export function translateRunFrame({ kind, raw, notices }) {
|
|
267
|
+
switch (kind) {
|
|
268
|
+
case "agent": {
|
|
269
|
+
const frame = parseWire(raw);
|
|
270
|
+
const translated = frame && isRecord(frame.payload) && typeof frame.payload.type === "string" ? translateRunAgentPayload({ payload: frame.payload }) : null;
|
|
271
|
+
return { events: translated ? [translated] : [] };
|
|
272
|
+
}
|
|
273
|
+
case "stdout":
|
|
274
|
+
case "stderr":
|
|
275
|
+
return { events: chunkEvent(raw) };
|
|
276
|
+
case "error": {
|
|
277
|
+
const frame = parseWire(raw);
|
|
278
|
+
const message = wireString(frame?.payload?.message) || "agent run failed";
|
|
279
|
+
return { events: [{ kind: "status", label: message }], error: new Error(message) };
|
|
280
|
+
}
|
|
281
|
+
case "end":
|
|
282
|
+
return endOutcome(raw, notices);
|
|
283
|
+
default:
|
|
284
|
+
return { events: [] };
|
|
285
|
+
}
|
|
286
|
+
}
|
|
287
|
+
function isRecord(value) {
|
|
288
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
289
|
+
}
|
|
290
|
+
//# sourceMappingURL=entry.js.map
|
package/dist/core/todos.d.ts
CHANGED
|
@@ -15,7 +15,9 @@ export interface TodoItem {
|
|
|
15
15
|
activeForm?: string | undefined;
|
|
16
16
|
}
|
|
17
17
|
/** `true` when `name` is one of the accepted plan/TodoWrite tool-name spellings. */
|
|
18
|
-
export declare function isTodoWriteToolName(name
|
|
18
|
+
export declare function isTodoWriteToolName({ name }: {
|
|
19
|
+
name: string;
|
|
20
|
+
}): boolean;
|
|
19
21
|
/**
|
|
20
22
|
* Parse a plan-tool call's raw `input` into a normalized `TodoItem[]`,
|
|
21
23
|
* tolerating the several shapes different agent runtimes emit (`todos` vs
|
|
@@ -26,15 +28,21 @@ export declare function isTodoWriteToolName(name: string): boolean;
|
|
|
26
28
|
* @returns Normalized items; entries with no recognizable body text are dropped.
|
|
27
29
|
* @complexity O(n) in the number of raw plan entries.
|
|
28
30
|
*/
|
|
29
|
-
export declare function parseTodoWriteInput(input
|
|
31
|
+
export declare function parseTodoWriteInput({ input }: {
|
|
32
|
+
input: unknown;
|
|
33
|
+
}): TodoItem[];
|
|
30
34
|
/**
|
|
31
35
|
* Find the most recent plan-tool `tool_use` in a single turn's events and
|
|
32
36
|
* return its parsed items, or `[]` if this turn never wrote a plan.
|
|
33
37
|
* @complexity O(n), scanning from the end.
|
|
34
38
|
*/
|
|
35
|
-
export declare function latestTodosFromEvents(events
|
|
39
|
+
export declare function latestTodosFromEvents({ events }: {
|
|
40
|
+
events: AgentEvent[] | undefined;
|
|
41
|
+
}): TodoItem[];
|
|
36
42
|
/** The subset of {@link latestTodosFromEvents} not yet marked `completed`. */
|
|
37
|
-
export declare function unfinishedTodosFromEvents(events
|
|
43
|
+
export declare function unfinishedTodosFromEvents({ events }: {
|
|
44
|
+
events: AgentEvent[] | undefined;
|
|
45
|
+
}): TodoItem[];
|
|
38
46
|
/**
|
|
39
47
|
* Walk a conversation in reverse to find the most recent plan-tool
|
|
40
48
|
* `tool_use` across every message and return its raw (un-parsed) `input`, so
|
|
@@ -47,9 +55,11 @@ export declare function unfinishedTodosFromEvents(events: AgentEvent[] | undefin
|
|
|
47
55
|
* the first hit scanning backwards, so the common case (a recent plan
|
|
48
56
|
* update) is far cheaper.
|
|
49
57
|
*/
|
|
50
|
-
export declare function latestTodoWriteInputFromMessages(messages:
|
|
51
|
-
|
|
52
|
-
|
|
58
|
+
export declare function latestTodoWriteInputFromMessages({ messages }: {
|
|
59
|
+
messages: ReadonlyArray<{
|
|
60
|
+
events?: AgentEvent[] | undefined;
|
|
61
|
+
}> | undefined;
|
|
62
|
+
}): unknown | null;
|
|
53
63
|
/** Convenience alias for {@link latestTodoWriteInputFromMessages} matching the `latestTodoWriteInput()` name in the target API. */
|
|
54
64
|
export declare const latestTodoWriteInput: typeof latestTodoWriteInputFromMessages;
|
|
55
65
|
/**
|
|
@@ -66,5 +76,7 @@ export declare function latestTodoWriteInputForPinnedCard<T extends {
|
|
|
66
76
|
events?: AgentEvent[] | undefined;
|
|
67
77
|
runStatus?: ChatRunStatus | undefined;
|
|
68
78
|
endedAt?: number | undefined;
|
|
69
|
-
}>(messages
|
|
79
|
+
}>({ messages }: {
|
|
80
|
+
messages: ReadonlyArray<T> | undefined;
|
|
81
|
+
}): unknown | null;
|
|
70
82
|
//# sourceMappingURL=todos.d.ts.map
|
package/dist/core/todos.js
CHANGED
|
@@ -5,7 +5,7 @@ const TODO_WRITE_TOOL_NAMES = new Set([
|
|
|
5
5
|
'update_plan',
|
|
6
6
|
]);
|
|
7
7
|
/** `true` when `name` is one of the accepted plan/TodoWrite tool-name spellings. */
|
|
8
|
-
export function isTodoWriteToolName(name) {
|
|
8
|
+
export function isTodoWriteToolName({ name }) {
|
|
9
9
|
return TODO_WRITE_TOOL_NAMES.has(name);
|
|
10
10
|
}
|
|
11
11
|
function normalizeTodoStatus(status) {
|
|
@@ -27,7 +27,7 @@ function normalizeTodoStatus(status) {
|
|
|
27
27
|
* @returns Normalized items; entries with no recognizable body text are dropped.
|
|
28
28
|
* @complexity O(n) in the number of raw plan entries.
|
|
29
29
|
*/
|
|
30
|
-
export function parseTodoWriteInput(input) {
|
|
30
|
+
export function parseTodoWriteInput({ input }) {
|
|
31
31
|
if (!input || typeof input !== 'object')
|
|
32
32
|
return [];
|
|
33
33
|
const obj = input;
|
|
@@ -67,20 +67,20 @@ export function parseTodoWriteInput(input) {
|
|
|
67
67
|
* return its parsed items, or `[]` if this turn never wrote a plan.
|
|
68
68
|
* @complexity O(n), scanning from the end.
|
|
69
69
|
*/
|
|
70
|
-
export function latestTodosFromEvents(events) {
|
|
70
|
+
export function latestTodosFromEvents({ events }) {
|
|
71
71
|
if (!events)
|
|
72
72
|
return [];
|
|
73
73
|
for (let i = events.length - 1; i >= 0; i -= 1) {
|
|
74
74
|
const event = events[i];
|
|
75
|
-
if (event?.kind !== 'tool_use' || !isTodoWriteToolName(event.name))
|
|
75
|
+
if (event?.kind !== 'tool_use' || !isTodoWriteToolName({ name: event.name }))
|
|
76
76
|
continue;
|
|
77
|
-
return parseTodoWriteInput(event.input);
|
|
77
|
+
return parseTodoWriteInput({ input: event.input });
|
|
78
78
|
}
|
|
79
79
|
return [];
|
|
80
80
|
}
|
|
81
81
|
/** The subset of {@link latestTodosFromEvents} not yet marked `completed`. */
|
|
82
|
-
export function unfinishedTodosFromEvents(events) {
|
|
83
|
-
return latestTodosFromEvents(events).filter((todo) => todo.status !== 'completed');
|
|
82
|
+
export function unfinishedTodosFromEvents({ events }) {
|
|
83
|
+
return latestTodosFromEvents({ events: events }).filter((todo) => todo.status !== 'completed');
|
|
84
84
|
}
|
|
85
85
|
/**
|
|
86
86
|
* Walk a conversation in reverse to find the most recent plan-tool
|
|
@@ -94,7 +94,7 @@ export function unfinishedTodosFromEvents(events) {
|
|
|
94
94
|
* the first hit scanning backwards, so the common case (a recent plan
|
|
95
95
|
* update) is far cheaper.
|
|
96
96
|
*/
|
|
97
|
-
export function latestTodoWriteInputFromMessages(messages) {
|
|
97
|
+
export function latestTodoWriteInputFromMessages({ messages }) {
|
|
98
98
|
if (!messages || messages.length === 0)
|
|
99
99
|
return null;
|
|
100
100
|
for (let mi = messages.length - 1; mi >= 0; mi -= 1) {
|
|
@@ -105,7 +105,7 @@ export function latestTodoWriteInputFromMessages(messages) {
|
|
|
105
105
|
const event = events[ei];
|
|
106
106
|
if (event?.kind !== 'tool_use')
|
|
107
107
|
continue;
|
|
108
|
-
if (!isTodoWriteToolName(event.name))
|
|
108
|
+
if (!isTodoWriteToolName({ name: event.name }))
|
|
109
109
|
continue;
|
|
110
110
|
return event.input;
|
|
111
111
|
}
|
|
@@ -150,7 +150,7 @@ function stoppedTodoWriteInput(input) {
|
|
|
150
150
|
* @complexity Same as {@link latestTodoWriteInputFromMessages}, plus an O(m)
|
|
151
151
|
* remap of the winning turn's items when the run has ended.
|
|
152
152
|
*/
|
|
153
|
-
export function latestTodoWriteInputForPinnedCard(messages) {
|
|
153
|
+
export function latestTodoWriteInputForPinnedCard({ messages }) {
|
|
154
154
|
if (!messages || messages.length === 0)
|
|
155
155
|
return null;
|
|
156
156
|
for (let mi = messages.length - 1; mi >= 0; mi -= 1) {
|
|
@@ -162,7 +162,7 @@ export function latestTodoWriteInputForPinnedCard(messages) {
|
|
|
162
162
|
const event = events[ei];
|
|
163
163
|
if (event?.kind !== 'tool_use')
|
|
164
164
|
continue;
|
|
165
|
-
if (!isTodoWriteToolName(event.name))
|
|
165
|
+
if (!isTodoWriteToolName({ name: event.name }))
|
|
166
166
|
continue;
|
|
167
167
|
if (!hasTerminalRunEnded(message.runStatus, message.endedAt)) {
|
|
168
168
|
return event.input;
|
|
@@ -14,5 +14,7 @@ import type { AgentEvent } from './events.js';
|
|
|
14
14
|
* `k` is the number of distinct `tool_use` ids seen — one linear pass with
|
|
15
15
|
* a `Set` membership check.
|
|
16
16
|
*/
|
|
17
|
-
export declare function dedupeToolUsesById(events
|
|
17
|
+
export declare function dedupeToolUsesById({ events }: {
|
|
18
|
+
events: AgentEvent[] | undefined;
|
|
19
|
+
}): AgentEvent[];
|
|
18
20
|
//# sourceMappingURL=tool-events.d.ts.map
|
package/dist/core/tool-events.js
CHANGED
|
@@ -13,7 +13,7 @@
|
|
|
13
13
|
* `k` is the number of distinct `tool_use` ids seen — one linear pass with
|
|
14
14
|
* a `Set` membership check.
|
|
15
15
|
*/
|
|
16
|
-
export function dedupeToolUsesById(events) {
|
|
16
|
+
export function dedupeToolUsesById({ events }) {
|
|
17
17
|
if (!events || events.length === 0)
|
|
18
18
|
return [];
|
|
19
19
|
const seen = new Set();
|
|
@@ -9,5 +9,7 @@
|
|
|
9
9
|
* @returns The value re-serialized with two-space indentation, or `text` as given.
|
|
10
10
|
* @complexity O(n) in `text.length`.
|
|
11
11
|
*/
|
|
12
|
-
export declare function formatToolOutputForDisplay(text
|
|
12
|
+
export declare function formatToolOutputForDisplay({ text }: {
|
|
13
|
+
text: string;
|
|
14
|
+
}): string;
|
|
13
15
|
//# sourceMappingURL=tool-output.d.ts.map
|
package/dist/core/tool-output.js
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
* @returns The value re-serialized with two-space indentation, or `text` as given.
|
|
10
10
|
* @complexity O(n) in `text.length`.
|
|
11
11
|
*/
|
|
12
|
-
export function formatToolOutputForDisplay(text) {
|
|
12
|
+
export function formatToolOutputForDisplay({ text }) {
|
|
13
13
|
const trimmed = text.trim();
|
|
14
14
|
const first = trimmed[0];
|
|
15
15
|
if (first !== '{' && first !== '[')
|
package/dist/core/tools.d.ts
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
* `runtime/tool-renderers.ts`) — that is a presentational, React-facing
|
|
8
8
|
* extension point that belongs to `@jini-ai/chat-react` (or
|
|
9
9
|
* `@jini-ai/renderers-react`), not this framework-free package. See
|
|
10
|
-
*
|
|
10
|
+
* archived provenance ledger.
|
|
11
11
|
*/
|
|
12
12
|
import type { ToolResultEvent, ToolResultMediaBlock, ToolUseEvent } from './events.js';
|
|
13
13
|
export { dedupeToolUsesById } from './tool-events.js';
|
|
@@ -40,12 +40,23 @@ export interface ToolRenderProps {
|
|
|
40
40
|
* @param runSucceeded - Whether the (already-terminal) run succeeded. Ignored while `runStreaming` is true.
|
|
41
41
|
* @complexity O(1).
|
|
42
42
|
*/
|
|
43
|
-
export declare function deriveToolStatus(result
|
|
43
|
+
export declare function deriveToolStatus({ result, runStreaming }: {
|
|
44
|
+
result: ToolResultEvent | undefined;
|
|
45
|
+
runStreaming: boolean;
|
|
46
|
+
}, { runSucceeded }?: {
|
|
47
|
+
runSucceeded?: (boolean) | undefined;
|
|
48
|
+
}): ToolStatus;
|
|
44
49
|
/**
|
|
45
50
|
* Project a `tool_use`/`tool_result` pair plus run state into the render-prop
|
|
46
51
|
* shape a tool-call UI consumes.
|
|
47
52
|
*
|
|
48
53
|
* @complexity O(1) — delegates its only branching to {@link deriveToolStatus}.
|
|
49
54
|
*/
|
|
50
|
-
export declare function toRenderProps(use
|
|
55
|
+
export declare function toRenderProps({ use, result, runStreaming }: {
|
|
56
|
+
use: ToolUseEvent;
|
|
57
|
+
result: ToolResultEvent | undefined;
|
|
58
|
+
runStreaming: boolean;
|
|
59
|
+
}, { runSucceeded }?: {
|
|
60
|
+
runSucceeded?: (boolean) | undefined;
|
|
61
|
+
}): ToolRenderProps;
|
|
51
62
|
//# sourceMappingURL=tools.d.ts.map
|
package/dist/core/tools.js
CHANGED
|
@@ -15,7 +15,7 @@ export { dedupeToolUsesById } from './tool-events.js';
|
|
|
15
15
|
* @param runSucceeded - Whether the (already-terminal) run succeeded. Ignored while `runStreaming` is true.
|
|
16
16
|
* @complexity O(1).
|
|
17
17
|
*/
|
|
18
|
-
export function deriveToolStatus(result, runStreaming, runSucceeded = false) {
|
|
18
|
+
export function deriveToolStatus({ result, runStreaming }, { runSucceeded = false } = {}) {
|
|
19
19
|
if (result)
|
|
20
20
|
return result.isError ? 'error' : 'complete';
|
|
21
21
|
if (runStreaming)
|
|
@@ -28,9 +28,9 @@ export function deriveToolStatus(result, runStreaming, runSucceeded = false) {
|
|
|
28
28
|
*
|
|
29
29
|
* @complexity O(1) — delegates its only branching to {@link deriveToolStatus}.
|
|
30
30
|
*/
|
|
31
|
-
export function toRenderProps(use, result, runStreaming, runSucceeded = false) {
|
|
31
|
+
export function toRenderProps({ use, result, runStreaming }, { runSucceeded = false } = {}) {
|
|
32
32
|
return {
|
|
33
|
-
status: deriveToolStatus(result, runStreaming, runSucceeded),
|
|
33
|
+
status: deriveToolStatus({ result: result, runStreaming: runStreaming }, { runSucceeded: runSucceeded }),
|
|
34
34
|
name: use.name,
|
|
35
35
|
args: use.input,
|
|
36
36
|
result: result?.content,
|