@ai-sdk/workflow 2.0.16 → 2.0.18
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 +20 -0
- package/dist/index.d.ts +27 -3
- package/dist/index.js +94 -152
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
- package/src/stream-text-iterator.ts +2 -1
- package/src/workflow-agent.ts +102 -131
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ai-sdk/workflow",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.18",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "WorkflowAgent for building AI agents with AI SDK",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -33,7 +33,7 @@
|
|
|
33
33
|
"dependencies": {
|
|
34
34
|
"@ai-sdk/provider": "4.0.9",
|
|
35
35
|
"@ai-sdk/provider-utils": "5.0.34",
|
|
36
|
-
"ai": "7.0.
|
|
36
|
+
"ai": "7.0.88",
|
|
37
37
|
"ajv": "^8.20.0"
|
|
38
38
|
},
|
|
39
39
|
"devDependencies": {
|
|
@@ -7,6 +7,7 @@ import type {
|
|
|
7
7
|
import type { Context } from '@ai-sdk/provider-utils';
|
|
8
8
|
import {
|
|
9
9
|
experimental_filterActiveTools as filterActiveTools,
|
|
10
|
+
type ActiveTools,
|
|
10
11
|
type Experimental_SandboxSession as SandboxSession,
|
|
11
12
|
type Instructions,
|
|
12
13
|
type LanguageModel,
|
|
@@ -164,7 +165,7 @@ export async function* streamTextIterator({
|
|
|
164
165
|
let currentRuntimeContext: Context = runtimeContext ?? {};
|
|
165
166
|
let currentToolsContext: Record<string, Context | undefined> =
|
|
166
167
|
toolsContext ?? {};
|
|
167
|
-
let currentActiveTools:
|
|
168
|
+
let currentActiveTools: ActiveTools<ToolSet>;
|
|
168
169
|
|
|
169
170
|
const steps: StepResult<any, any>[] = [];
|
|
170
171
|
let done = false;
|
package/src/workflow-agent.ts
CHANGED
|
@@ -28,6 +28,7 @@ import {
|
|
|
28
28
|
type ToolCallRepairFunction,
|
|
29
29
|
type ToolChoice,
|
|
30
30
|
type ToolSet,
|
|
31
|
+
type InferUITools,
|
|
31
32
|
type UIMessage,
|
|
32
33
|
type LanguageModel,
|
|
33
34
|
type Prompt,
|
|
@@ -84,9 +85,13 @@ export type InferWorkflowAgentTools<WORKFLOW_AGENT> =
|
|
|
84
85
|
* Infer the UI message type of a workflow agent.
|
|
85
86
|
*/
|
|
86
87
|
export type InferWorkflowAgentUIMessage<
|
|
87
|
-
|
|
88
|
+
WORKFLOW_AGENT,
|
|
88
89
|
MESSAGE_METADATA = unknown,
|
|
89
|
-
> = UIMessage<
|
|
90
|
+
> = UIMessage<
|
|
91
|
+
MESSAGE_METADATA,
|
|
92
|
+
never,
|
|
93
|
+
InferUITools<InferWorkflowAgentTools<WORKFLOW_AGENT>>
|
|
94
|
+
>;
|
|
90
95
|
|
|
91
96
|
/**
|
|
92
97
|
* Re-export the Output helper for structured output specifications.
|
|
@@ -349,7 +354,7 @@ export interface PrepareStepResult<
|
|
|
349
354
|
* Override the active tools for this step.
|
|
350
355
|
* Limits the tools that are available for the model to call.
|
|
351
356
|
*/
|
|
352
|
-
activeTools?:
|
|
357
|
+
activeTools?: ActiveTools<NoInfer<TTools>>;
|
|
353
358
|
|
|
354
359
|
/**
|
|
355
360
|
* Updated runtime context for the current and subsequent steps.
|
|
@@ -605,6 +610,13 @@ export type WorkflowAgentOptions<
|
|
|
605
610
|
/**
|
|
606
611
|
* Callback called when the agent starts streaming, before any LLM calls.
|
|
607
612
|
*/
|
|
613
|
+
onStart?: WorkflowAgentOnStartCallback<TTools, TRuntimeContext>;
|
|
614
|
+
|
|
615
|
+
/**
|
|
616
|
+
* Callback called when the agent starts streaming, before any LLM calls.
|
|
617
|
+
*
|
|
618
|
+
* @deprecated Use `onStart` instead.
|
|
619
|
+
*/
|
|
608
620
|
experimental_onStart?: WorkflowAgentOnStartCallback<
|
|
609
621
|
TTools,
|
|
610
622
|
TRuntimeContext
|
|
@@ -613,6 +625,13 @@ export type WorkflowAgentOptions<
|
|
|
613
625
|
/**
|
|
614
626
|
* Callback called before each step (LLM call) begins.
|
|
615
627
|
*/
|
|
628
|
+
onStepStart?: WorkflowAgentOnStepStartCallback<TTools, TRuntimeContext>;
|
|
629
|
+
|
|
630
|
+
/**
|
|
631
|
+
* Callback called before each step (LLM call) begins.
|
|
632
|
+
*
|
|
633
|
+
* @deprecated Use `onStepStart` instead.
|
|
634
|
+
*/
|
|
616
635
|
experimental_onStepStart?: WorkflowAgentOnStepStartCallback<
|
|
617
636
|
TTools,
|
|
618
637
|
TRuntimeContext
|
|
@@ -1080,6 +1099,13 @@ export type WorkflowAgentStreamOptions<
|
|
|
1080
1099
|
/**
|
|
1081
1100
|
* Callback called when the agent starts streaming, before any LLM calls.
|
|
1082
1101
|
*/
|
|
1102
|
+
onStart?: WorkflowAgentOnStartCallback<TTools, TRuntimeContext>;
|
|
1103
|
+
|
|
1104
|
+
/**
|
|
1105
|
+
* Callback called when the agent starts streaming, before any LLM calls.
|
|
1106
|
+
*
|
|
1107
|
+
* @deprecated Use `onStart` instead.
|
|
1108
|
+
*/
|
|
1083
1109
|
experimental_onStart?: WorkflowAgentOnStartCallback<
|
|
1084
1110
|
TTools,
|
|
1085
1111
|
TRuntimeContext
|
|
@@ -1088,6 +1114,13 @@ export type WorkflowAgentStreamOptions<
|
|
|
1088
1114
|
/**
|
|
1089
1115
|
* Callback called before each step (LLM call) begins.
|
|
1090
1116
|
*/
|
|
1117
|
+
onStepStart?: WorkflowAgentOnStepStartCallback<TTools, TRuntimeContext>;
|
|
1118
|
+
|
|
1119
|
+
/**
|
|
1120
|
+
* Callback called before each step (LLM call) begins.
|
|
1121
|
+
*
|
|
1122
|
+
* @deprecated Use `onStepStart` instead.
|
|
1123
|
+
*/
|
|
1091
1124
|
experimental_onStepStart?: WorkflowAgentOnStepStartCallback<
|
|
1092
1125
|
TTools,
|
|
1093
1126
|
TRuntimeContext
|
|
@@ -1350,8 +1383,9 @@ export class WorkflowAgent<
|
|
|
1350
1383
|
this.constructorOnStepEnd = options.onStepEnd ?? options.onStepFinish;
|
|
1351
1384
|
const { onFinish, onEnd = onFinish } = options;
|
|
1352
1385
|
this.constructorOnEnd = onEnd;
|
|
1353
|
-
this.constructorOnStart = options.experimental_onStart;
|
|
1354
|
-
this.constructorOnStepStart =
|
|
1386
|
+
this.constructorOnStart = options.onStart ?? options.experimental_onStart;
|
|
1387
|
+
this.constructorOnStepStart =
|
|
1388
|
+
options.onStepStart ?? options.experimental_onStepStart;
|
|
1355
1389
|
this.constructorOnToolExecutionStart = options.onToolExecutionStart;
|
|
1356
1390
|
this.constructorOnToolExecutionEnd = options.onToolExecutionEnd;
|
|
1357
1391
|
this.prepareCall = options.prepareCall;
|
|
@@ -1518,6 +1552,14 @@ export class WorkflowAgent<
|
|
|
1518
1552
|
} as Prompt);
|
|
1519
1553
|
const download = effectiveDownloadFromPrepare;
|
|
1520
1554
|
const sandbox = options.experimental_sandbox ?? this.experimentalSandbox;
|
|
1555
|
+
const mergedOnToolExecutionStart = mergeCallbacks(
|
|
1556
|
+
this.constructorOnToolExecutionStart,
|
|
1557
|
+
options.onToolExecutionStart,
|
|
1558
|
+
);
|
|
1559
|
+
const mergedOnToolExecutionEnd = mergeCallbacks(
|
|
1560
|
+
this.constructorOnToolExecutionEnd,
|
|
1561
|
+
options.onToolExecutionEnd,
|
|
1562
|
+
);
|
|
1521
1563
|
|
|
1522
1564
|
// Process tool approval responses before starting the agent loop.
|
|
1523
1565
|
// This mirrors how stream-text.ts handles tool-approval-response parts:
|
|
@@ -1663,110 +1705,25 @@ export class WorkflowAgent<
|
|
|
1663
1705
|
continue;
|
|
1664
1706
|
}
|
|
1665
1707
|
|
|
1666
|
-
|
|
1667
|
-
|
|
1668
|
-
const resolvedContext = await resolveToolContext({
|
|
1669
|
-
toolName: approval.toolName,
|
|
1670
|
-
tool,
|
|
1671
|
-
toolsContext: effectiveToolsContext,
|
|
1672
|
-
});
|
|
1673
|
-
const toolCallEvent: ToolCall = {
|
|
1674
|
-
type: 'tool-call',
|
|
1675
|
-
toolCallId: approval.toolCallId,
|
|
1676
|
-
toolName: approval.toolName,
|
|
1677
|
-
input: approval.input,
|
|
1678
|
-
};
|
|
1679
|
-
const messages = prompt.messages as unknown as ModelMessage[];
|
|
1680
|
-
await telemetryDispatcher.onToolExecutionStart?.({
|
|
1681
|
-
toolCall: toolCallEvent,
|
|
1682
|
-
stepNumber: 0,
|
|
1683
|
-
messages,
|
|
1684
|
-
toolContext: resolvedContext,
|
|
1685
|
-
});
|
|
1686
|
-
const startTime = Date.now();
|
|
1687
|
-
const executeApprovedTool = () =>
|
|
1688
|
-
execute(approval.input, {
|
|
1689
|
-
toolCallId: approval.toolCallId,
|
|
1690
|
-
messages: [],
|
|
1691
|
-
context: resolvedContext,
|
|
1692
|
-
experimental_sandbox: sandbox,
|
|
1693
|
-
});
|
|
1694
|
-
const toolResult =
|
|
1695
|
-
telemetryDispatcher.executeTool != null
|
|
1696
|
-
? await telemetryDispatcher.executeTool({
|
|
1697
|
-
callId: 'workflow-agent',
|
|
1698
|
-
toolCallId: approval.toolCallId,
|
|
1699
|
-
execute: executeApprovedTool,
|
|
1700
|
-
})
|
|
1701
|
-
: await executeApprovedTool();
|
|
1702
|
-
await telemetryDispatcher.onToolExecutionEnd?.({
|
|
1703
|
-
toolCall: toolCallEvent,
|
|
1704
|
-
stepNumber: 0,
|
|
1705
|
-
durationMs: Date.now() - startTime,
|
|
1706
|
-
messages,
|
|
1707
|
-
toolContext: resolvedContext,
|
|
1708
|
-
success: true,
|
|
1709
|
-
output: toolResult,
|
|
1710
|
-
});
|
|
1711
|
-
toolResultContent.push({
|
|
1712
|
-
type: 'tool-result' as const,
|
|
1713
|
-
toolCallId: approval.toolCallId,
|
|
1714
|
-
toolName: approval.toolName,
|
|
1715
|
-
output: await createLanguageModelToolResultOutput({
|
|
1716
|
-
toolCallId: approval.toolCallId,
|
|
1717
|
-
toolName: approval.toolName,
|
|
1718
|
-
input: approval.input,
|
|
1719
|
-
output: toolResult,
|
|
1720
|
-
tool,
|
|
1721
|
-
errorMode: 'none',
|
|
1722
|
-
supportedUrls: {},
|
|
1723
|
-
download,
|
|
1724
|
-
}),
|
|
1725
|
-
});
|
|
1726
|
-
approvedRawResults.push({
|
|
1727
|
-
toolCallId: approval.toolCallId,
|
|
1728
|
-
toolName: approval.toolName,
|
|
1729
|
-
input: approval.input,
|
|
1730
|
-
output: toolResult,
|
|
1731
|
-
});
|
|
1732
|
-
} catch (error) {
|
|
1733
|
-
const errorMessage = getErrorMessage(error);
|
|
1734
|
-
await telemetryDispatcher.onToolExecutionEnd?.({
|
|
1735
|
-
toolCall: {
|
|
1736
|
-
type: 'tool-call',
|
|
1737
|
-
toolCallId: approval.toolCallId,
|
|
1738
|
-
toolName: approval.toolName,
|
|
1739
|
-
input: approval.input,
|
|
1740
|
-
},
|
|
1741
|
-
stepNumber: 0,
|
|
1742
|
-
durationMs: 0,
|
|
1743
|
-
messages: prompt.messages as unknown as ModelMessage[],
|
|
1744
|
-
toolContext: undefined,
|
|
1745
|
-
success: false,
|
|
1746
|
-
error,
|
|
1747
|
-
});
|
|
1748
|
-
toolResultContent.push({
|
|
1749
|
-
type: 'tool-result' as const,
|
|
1750
|
-
toolCallId: approval.toolCallId,
|
|
1751
|
-
toolName: approval.toolName,
|
|
1752
|
-
output: await createLanguageModelToolResultOutput({
|
|
1753
|
-
toolCallId: approval.toolCallId,
|
|
1754
|
-
toolName: approval.toolName,
|
|
1755
|
-
input: approval.input,
|
|
1756
|
-
output: errorMessage,
|
|
1757
|
-
tool,
|
|
1758
|
-
errorMode: 'text',
|
|
1759
|
-
supportedUrls: {},
|
|
1760
|
-
download,
|
|
1761
|
-
}),
|
|
1762
|
-
});
|
|
1763
|
-
approvedRawResults.push({
|
|
1708
|
+
const result = await executeToolWithCallbacks(
|
|
1709
|
+
{
|
|
1764
1710
|
toolCallId: approval.toolCallId,
|
|
1765
1711
|
toolName: approval.toolName,
|
|
1766
1712
|
input: approval.input,
|
|
1767
|
-
|
|
1768
|
-
|
|
1769
|
-
|
|
1713
|
+
},
|
|
1714
|
+
this.tools as ToolSet,
|
|
1715
|
+
prompt.messages as unknown as LanguageModelV4Prompt,
|
|
1716
|
+
effectiveToolsContext,
|
|
1717
|
+
0,
|
|
1718
|
+
sandbox,
|
|
1719
|
+
);
|
|
1720
|
+
toolResultContent.push(result.modelResult);
|
|
1721
|
+
approvedRawResults.push({
|
|
1722
|
+
toolCallId: approval.toolCallId,
|
|
1723
|
+
toolName: approval.toolName,
|
|
1724
|
+
input: approval.input,
|
|
1725
|
+
output: result.rawOutput,
|
|
1726
|
+
});
|
|
1770
1727
|
}
|
|
1771
1728
|
}
|
|
1772
1729
|
|
|
@@ -1918,23 +1875,14 @@ export class WorkflowAgent<
|
|
|
1918
1875
|
this.constructorOnStart as
|
|
1919
1876
|
| WorkflowAgentOnStartCallback<TTools, TRuntimeContext>
|
|
1920
1877
|
| undefined,
|
|
1921
|
-
options.experimental_onStart,
|
|
1878
|
+
options.onStart ?? options.experimental_onStart,
|
|
1922
1879
|
);
|
|
1923
1880
|
const mergedOnStepStart = mergeCallbacks(
|
|
1924
1881
|
this.constructorOnStepStart as
|
|
1925
1882
|
| WorkflowAgentOnStepStartCallback<TTools, TRuntimeContext>
|
|
1926
1883
|
| undefined,
|
|
1927
|
-
options.experimental_onStepStart,
|
|
1928
|
-
);
|
|
1929
|
-
const mergedOnToolExecutionStart = mergeCallbacks(
|
|
1930
|
-
this.constructorOnToolExecutionStart,
|
|
1931
|
-
options.onToolExecutionStart,
|
|
1884
|
+
options.onStepStart ?? options.experimental_onStepStart,
|
|
1932
1885
|
);
|
|
1933
|
-
const mergedOnToolExecutionEnd = mergeCallbacks(
|
|
1934
|
-
this.constructorOnToolExecutionEnd,
|
|
1935
|
-
options.onToolExecutionEnd,
|
|
1936
|
-
);
|
|
1937
|
-
|
|
1938
1886
|
// Determine effective tool choice
|
|
1939
1887
|
const effectiveToolChoice = effectiveToolChoiceFromPrepare;
|
|
1940
1888
|
|
|
@@ -1998,14 +1946,14 @@ export class WorkflowAgent<
|
|
|
1998
1946
|
});
|
|
1999
1947
|
|
|
2000
1948
|
// Helper to wrap executeTool with onToolExecutionStart/onToolExecutionEnd callbacks
|
|
2001
|
-
|
|
1949
|
+
async function executeToolWithCallbacks(
|
|
2002
1950
|
toolCall: { toolCallId: string; toolName: string; input: unknown },
|
|
2003
1951
|
tools: ToolSet,
|
|
2004
1952
|
messages: LanguageModelV4Prompt,
|
|
2005
1953
|
perToolContexts: Record<string, Context | undefined>,
|
|
2006
1954
|
currentStepNumber: number = 0,
|
|
2007
1955
|
stepSandbox?: SandboxSession,
|
|
2008
|
-
): Promise<WorkflowToolExecutionResult>
|
|
1956
|
+
): Promise<WorkflowToolExecutionResult> {
|
|
2009
1957
|
const toolCallEvent: ToolCall = {
|
|
2010
1958
|
type: 'tool-call',
|
|
2011
1959
|
toolCallId: toolCall.toolCallId,
|
|
@@ -2145,7 +2093,7 @@ export class WorkflowAgent<
|
|
|
2145
2093
|
});
|
|
2146
2094
|
}
|
|
2147
2095
|
return result;
|
|
2148
|
-
}
|
|
2096
|
+
}
|
|
2149
2097
|
|
|
2150
2098
|
const recordProviderExecutedToolTelemetry = async (
|
|
2151
2099
|
toolCall: { toolCallId: string; toolName: string; input: unknown },
|
|
@@ -2437,7 +2385,18 @@ export class WorkflowAgent<
|
|
|
2437
2385
|
// so useChat can show the approval UI
|
|
2438
2386
|
if (options.writable) {
|
|
2439
2387
|
if (allToolResults.length > 0) {
|
|
2440
|
-
await writeToolResults(
|
|
2388
|
+
await writeToolResults(
|
|
2389
|
+
options.writable,
|
|
2390
|
+
executedResults.map(r => ({
|
|
2391
|
+
toolCallId: r.modelResult.toolCallId,
|
|
2392
|
+
toolName: r.modelResult.toolName,
|
|
2393
|
+
input: toolCalls.find(
|
|
2394
|
+
tc => tc.toolCallId === r.modelResult.toolCallId,
|
|
2395
|
+
)?.input,
|
|
2396
|
+
output: r.rawOutput,
|
|
2397
|
+
isError: r.isError,
|
|
2398
|
+
})),
|
|
2399
|
+
);
|
|
2441
2400
|
}
|
|
2442
2401
|
|
|
2443
2402
|
const approvalToolCalls = pausedToolCalls.filter((_, i) => {
|
|
@@ -2562,9 +2521,9 @@ export class WorkflowAgent<
|
|
|
2562
2521
|
return [];
|
|
2563
2522
|
});
|
|
2564
2523
|
|
|
2565
|
-
// Write tool results and step boundaries to the stream so the
|
|
2566
|
-
//
|
|
2567
|
-
//
|
|
2524
|
+
// Write tool results and step boundaries to the stream so the UI can
|
|
2525
|
+
// transition tool parts to the appropriate output state and properly
|
|
2526
|
+
// separate multi-step model calls in the message history.
|
|
2568
2527
|
if (options.writable) {
|
|
2569
2528
|
await writeToolResults(
|
|
2570
2529
|
options.writable,
|
|
@@ -2575,6 +2534,7 @@ export class WorkflowAgent<
|
|
|
2575
2534
|
tc => tc.toolCallId === r.modelResult.toolCallId,
|
|
2576
2535
|
)?.input,
|
|
2577
2536
|
output: r.rawOutput,
|
|
2537
|
+
isError: r.isError,
|
|
2578
2538
|
})),
|
|
2579
2539
|
true,
|
|
2580
2540
|
);
|
|
@@ -2937,6 +2897,7 @@ async function writeToolResults(
|
|
|
2937
2897
|
toolName: string;
|
|
2938
2898
|
input: unknown;
|
|
2939
2899
|
output: unknown;
|
|
2900
|
+
isError: boolean;
|
|
2940
2901
|
}>,
|
|
2941
2902
|
writeStepBoundary = false,
|
|
2942
2903
|
) {
|
|
@@ -2944,13 +2905,23 @@ async function writeToolResults(
|
|
|
2944
2905
|
const writer = writable.getWriter();
|
|
2945
2906
|
try {
|
|
2946
2907
|
for (const r of results) {
|
|
2947
|
-
await writer.write(
|
|
2948
|
-
|
|
2949
|
-
|
|
2950
|
-
|
|
2951
|
-
|
|
2952
|
-
|
|
2953
|
-
|
|
2908
|
+
await writer.write(
|
|
2909
|
+
r.isError
|
|
2910
|
+
? {
|
|
2911
|
+
type: 'tool-error',
|
|
2912
|
+
toolCallId: r.toolCallId,
|
|
2913
|
+
toolName: r.toolName,
|
|
2914
|
+
input: r.input,
|
|
2915
|
+
error: r.output,
|
|
2916
|
+
}
|
|
2917
|
+
: {
|
|
2918
|
+
type: 'tool-result',
|
|
2919
|
+
toolCallId: r.toolCallId,
|
|
2920
|
+
toolName: r.toolName,
|
|
2921
|
+
input: r.input,
|
|
2922
|
+
output: r.output,
|
|
2923
|
+
},
|
|
2924
|
+
);
|
|
2954
2925
|
}
|
|
2955
2926
|
if (writeStepBoundary) {
|
|
2956
2927
|
// Emit step boundaries so the UI message history properly separates
|