@ai-sdk/openai 4.0.14 → 4.0.16
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 +17 -0
- package/dist/index.d.ts +285 -24
- package/dist/index.js +1525 -1169
- package/dist/index.js.map +1 -1
- package/dist/internal/index.d.ts +184 -8
- package/dist/internal/index.js +1467 -1121
- package/dist/internal/index.js.map +1 -1
- package/docs/03-openai.mdx +93 -4
- package/package.json +2 -2
- package/src/index.ts +4 -0
- package/src/openai-tools.ts +11 -0
- package/src/responses/convert-to-openai-responses-input.ts +83 -1
- package/src/responses/openai-responses-api.ts +96 -19
- package/src/responses/openai-responses-language-model.ts +179 -33
- package/src/responses/openai-responses-prepare-tools.ts +9 -1
- package/src/tool/computer.ts +147 -0
|
@@ -38,6 +38,7 @@ import type {
|
|
|
38
38
|
codeInterpreterInputSchema,
|
|
39
39
|
codeInterpreterOutputSchema,
|
|
40
40
|
} from '../tool/code-interpreter';
|
|
41
|
+
import type { computerInputSchema } from '../tool/computer';
|
|
41
42
|
import type { fileSearchOutputSchema } from '../tool/file-search';
|
|
42
43
|
import type { imageGenerationOutputSchema } from '../tool/image-generation';
|
|
43
44
|
import type { localShellInputSchema } from '../tool/local-shell';
|
|
@@ -64,6 +65,7 @@ import {
|
|
|
64
65
|
type OpenAIResponsesWebSearchAction,
|
|
65
66
|
type OpenAIResponsesApplyPatchOperationDiffDeltaChunk,
|
|
66
67
|
type OpenAIResponsesApplyPatchOperationDiffDoneChunk,
|
|
68
|
+
type OpenAIResponsesComputerAction,
|
|
67
69
|
} from './openai-responses-api';
|
|
68
70
|
import {
|
|
69
71
|
openaiLanguageModelResponsesOptionsSchema,
|
|
@@ -104,6 +106,87 @@ function extractApprovalRequestIdToToolCallIdMapping(
|
|
|
104
106
|
return mapping;
|
|
105
107
|
}
|
|
106
108
|
|
|
109
|
+
function mapComputerAction(
|
|
110
|
+
action: OpenAIResponsesComputerAction,
|
|
111
|
+
): InferSchema<typeof computerInputSchema>['actions'][number] {
|
|
112
|
+
switch (action.type) {
|
|
113
|
+
case 'click':
|
|
114
|
+
return {
|
|
115
|
+
type: 'click',
|
|
116
|
+
button: action.button,
|
|
117
|
+
x: action.x,
|
|
118
|
+
y: action.y,
|
|
119
|
+
...(action.keys != null && { keys: action.keys }),
|
|
120
|
+
};
|
|
121
|
+
case 'double_click':
|
|
122
|
+
return {
|
|
123
|
+
type: 'double_click',
|
|
124
|
+
x: action.x,
|
|
125
|
+
y: action.y,
|
|
126
|
+
...(action.keys != null && { keys: action.keys }),
|
|
127
|
+
};
|
|
128
|
+
case 'drag':
|
|
129
|
+
return {
|
|
130
|
+
type: 'drag',
|
|
131
|
+
path: action.path,
|
|
132
|
+
...(action.keys != null && { keys: action.keys }),
|
|
133
|
+
};
|
|
134
|
+
case 'keypress':
|
|
135
|
+
return action;
|
|
136
|
+
case 'move':
|
|
137
|
+
return {
|
|
138
|
+
type: 'move',
|
|
139
|
+
x: action.x,
|
|
140
|
+
y: action.y,
|
|
141
|
+
...(action.keys != null && { keys: action.keys }),
|
|
142
|
+
};
|
|
143
|
+
case 'screenshot':
|
|
144
|
+
return action;
|
|
145
|
+
case 'scroll':
|
|
146
|
+
return {
|
|
147
|
+
type: 'scroll',
|
|
148
|
+
x: action.x,
|
|
149
|
+
y: action.y,
|
|
150
|
+
scrollX: action.scroll_x,
|
|
151
|
+
scrollY: action.scroll_y,
|
|
152
|
+
...(action.keys != null && { keys: action.keys }),
|
|
153
|
+
};
|
|
154
|
+
case 'type':
|
|
155
|
+
return action;
|
|
156
|
+
case 'wait':
|
|
157
|
+
return action;
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
function mapComputerCallInput({
|
|
162
|
+
action,
|
|
163
|
+
actions,
|
|
164
|
+
pending_safety_checks,
|
|
165
|
+
status,
|
|
166
|
+
}: {
|
|
167
|
+
action?: OpenAIResponsesComputerAction | null;
|
|
168
|
+
actions?: OpenAIResponsesComputerAction[] | null;
|
|
169
|
+
pending_safety_checks?: Array<{
|
|
170
|
+
id: string;
|
|
171
|
+
code?: string | null;
|
|
172
|
+
message?: string | null;
|
|
173
|
+
}> | null;
|
|
174
|
+
status: 'in_progress' | 'completed' | 'incomplete';
|
|
175
|
+
}): InferSchema<typeof computerInputSchema> {
|
|
176
|
+
return {
|
|
177
|
+
actions: (actions ?? (action != null ? [action] : [])).map(
|
|
178
|
+
mapComputerAction,
|
|
179
|
+
),
|
|
180
|
+
pendingSafetyChecks:
|
|
181
|
+
pending_safety_checks?.map(safetyCheck => ({
|
|
182
|
+
id: safetyCheck.id,
|
|
183
|
+
...(safetyCheck.code != null && { code: safetyCheck.code }),
|
|
184
|
+
...(safetyCheck.message != null && { message: safetyCheck.message }),
|
|
185
|
+
})) ?? [],
|
|
186
|
+
status,
|
|
187
|
+
};
|
|
188
|
+
}
|
|
189
|
+
|
|
107
190
|
export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
108
191
|
readonly specificationVersion = 'v4';
|
|
109
192
|
|
|
@@ -220,6 +303,7 @@ export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
|
220
303
|
tools,
|
|
221
304
|
providerToolNames: {
|
|
222
305
|
'openai.code_interpreter': 'code_interpreter',
|
|
306
|
+
'openai.computer': 'computer',
|
|
223
307
|
'openai.file_search': 'file_search',
|
|
224
308
|
'openai.image_generation': 'image_generation',
|
|
225
309
|
'openai.local_shell': 'local_shell',
|
|
@@ -264,6 +348,7 @@ export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
|
264
348
|
hasLocalShellTool: hasOpenAITool('openai.local_shell'),
|
|
265
349
|
hasShellTool: hasOpenAITool('openai.shell'),
|
|
266
350
|
hasApplyPatchTool: hasOpenAITool('openai.apply_patch'),
|
|
351
|
+
hasComputerTool: hasOpenAITool('openai.computer'),
|
|
267
352
|
customProviderToolNames:
|
|
268
353
|
customProviderToolNames.size > 0
|
|
269
354
|
? customProviderToolNames
|
|
@@ -569,6 +654,21 @@ export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
|
569
654
|
});
|
|
570
655
|
}
|
|
571
656
|
|
|
657
|
+
if (response.output == null) {
|
|
658
|
+
const detail = response.incomplete_details?.reason;
|
|
659
|
+
throw new APICallError({
|
|
660
|
+
message: detail
|
|
661
|
+
? `Responses API returned no output (${detail})`
|
|
662
|
+
: 'Responses API returned no output',
|
|
663
|
+
url,
|
|
664
|
+
requestBodyValues: body,
|
|
665
|
+
statusCode: 500,
|
|
666
|
+
responseHeaders,
|
|
667
|
+
responseBody: rawResponse as string,
|
|
668
|
+
isRetryable: false,
|
|
669
|
+
});
|
|
670
|
+
}
|
|
671
|
+
|
|
572
672
|
const content: Array<LanguageModelV4Content> = [];
|
|
573
673
|
const logprobs: Array<OpenAIResponsesLogprobs> = [];
|
|
574
674
|
|
|
@@ -576,8 +676,8 @@ export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
|
576
676
|
let hasFunctionCall = false;
|
|
577
677
|
const hostedToolSearchCallIds: string[] = [];
|
|
578
678
|
|
|
579
|
-
// map response content to content array
|
|
580
|
-
for (const part of response.output
|
|
679
|
+
// map response content to content array
|
|
680
|
+
for (const part of response.output) {
|
|
581
681
|
switch (part.type) {
|
|
582
682
|
case 'reasoning': {
|
|
583
683
|
// when there are no summary parts, we need to add an empty reasoning part:
|
|
@@ -957,21 +1057,39 @@ export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
|
957
1057
|
}
|
|
958
1058
|
|
|
959
1059
|
case 'computer_call': {
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
1060
|
+
if (part.call_id == null) {
|
|
1061
|
+
content.push({
|
|
1062
|
+
type: 'tool-call',
|
|
1063
|
+
toolCallId: part.id,
|
|
1064
|
+
toolName: toolNameMapping.toCustomToolName('computer_use'),
|
|
1065
|
+
input: '',
|
|
1066
|
+
providerExecuted: true,
|
|
1067
|
+
});
|
|
1068
|
+
|
|
1069
|
+
content.push({
|
|
1070
|
+
type: 'tool-result',
|
|
1071
|
+
toolCallId: part.id,
|
|
1072
|
+
toolName: toolNameMapping.toCustomToolName('computer_use'),
|
|
1073
|
+
result: {
|
|
1074
|
+
type: 'computer_use_tool_result',
|
|
1075
|
+
status: part.status,
|
|
1076
|
+
},
|
|
1077
|
+
});
|
|
1078
|
+
break;
|
|
1079
|
+
}
|
|
1080
|
+
|
|
1081
|
+
hasFunctionCall = true;
|
|
1082
|
+
const toolName = toolNameMapping.toCustomToolName('computer');
|
|
967
1083
|
|
|
968
1084
|
content.push({
|
|
969
|
-
type: 'tool-
|
|
970
|
-
toolCallId: part.
|
|
971
|
-
toolName
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
1085
|
+
type: 'tool-call',
|
|
1086
|
+
toolCallId: part.call_id,
|
|
1087
|
+
toolName,
|
|
1088
|
+
input: JSON.stringify(mapComputerCallInput(part)),
|
|
1089
|
+
providerMetadata: {
|
|
1090
|
+
[providerOptionsName]: {
|
|
1091
|
+
itemId: part.id,
|
|
1092
|
+
},
|
|
975
1093
|
},
|
|
976
1094
|
});
|
|
977
1095
|
break;
|
|
@@ -1303,16 +1421,16 @@ export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
|
1303
1421
|
providerExecuted: true,
|
|
1304
1422
|
});
|
|
1305
1423
|
} else if (value.item.type === 'computer_call') {
|
|
1424
|
+
const toolCallId = value.item.call_id ?? value.item.id;
|
|
1306
1425
|
ongoingToolCalls[value.output_index] = {
|
|
1307
|
-
toolName: toolNameMapping.toCustomToolName('
|
|
1308
|
-
toolCallId
|
|
1426
|
+
toolName: toolNameMapping.toCustomToolName('computer'),
|
|
1427
|
+
toolCallId,
|
|
1309
1428
|
};
|
|
1310
1429
|
|
|
1311
1430
|
controller.enqueue({
|
|
1312
1431
|
type: 'tool-input-start',
|
|
1313
|
-
id:
|
|
1314
|
-
toolName: toolNameMapping.toCustomToolName('
|
|
1315
|
-
providerExecuted: true,
|
|
1432
|
+
id: toolCallId,
|
|
1433
|
+
toolName: toolNameMapping.toCustomToolName('computer'),
|
|
1316
1434
|
});
|
|
1317
1435
|
} else if (value.item.type === 'code_interpreter_call') {
|
|
1318
1436
|
ongoingToolCalls[value.output_index] = {
|
|
@@ -1553,26 +1671,54 @@ export class OpenAIResponsesLanguageModel implements LanguageModelV4 {
|
|
|
1553
1671
|
} else if (value.item.type === 'computer_call') {
|
|
1554
1672
|
ongoingToolCalls[value.output_index] = undefined;
|
|
1555
1673
|
|
|
1674
|
+
if (value.item.call_id == null) {
|
|
1675
|
+
controller.enqueue({
|
|
1676
|
+
type: 'tool-input-end',
|
|
1677
|
+
id: value.item.id,
|
|
1678
|
+
});
|
|
1679
|
+
controller.enqueue({
|
|
1680
|
+
type: 'tool-call',
|
|
1681
|
+
toolCallId: value.item.id,
|
|
1682
|
+
toolName: toolNameMapping.toCustomToolName('computer_use'),
|
|
1683
|
+
input: '',
|
|
1684
|
+
providerExecuted: true,
|
|
1685
|
+
});
|
|
1686
|
+
controller.enqueue({
|
|
1687
|
+
type: 'tool-result',
|
|
1688
|
+
toolCallId: value.item.id,
|
|
1689
|
+
toolName: toolNameMapping.toCustomToolName('computer_use'),
|
|
1690
|
+
result: {
|
|
1691
|
+
type: 'computer_use_tool_result',
|
|
1692
|
+
status: value.item.status,
|
|
1693
|
+
},
|
|
1694
|
+
});
|
|
1695
|
+
return;
|
|
1696
|
+
}
|
|
1697
|
+
|
|
1698
|
+
hasFunctionCall = true;
|
|
1699
|
+
const toolName = toolNameMapping.toCustomToolName('computer');
|
|
1700
|
+
const input = JSON.stringify(mapComputerCallInput(value.item));
|
|
1701
|
+
|
|
1556
1702
|
controller.enqueue({
|
|
1557
|
-
type: 'tool-input-
|
|
1558
|
-
id: value.item.
|
|
1703
|
+
type: 'tool-input-delta',
|
|
1704
|
+
id: value.item.call_id,
|
|
1705
|
+
delta: input,
|
|
1559
1706
|
});
|
|
1560
1707
|
|
|
1561
1708
|
controller.enqueue({
|
|
1562
|
-
type: 'tool-
|
|
1563
|
-
|
|
1564
|
-
toolName: toolNameMapping.toCustomToolName('computer_use'),
|
|
1565
|
-
input: '',
|
|
1566
|
-
providerExecuted: true,
|
|
1709
|
+
type: 'tool-input-end',
|
|
1710
|
+
id: value.item.call_id,
|
|
1567
1711
|
});
|
|
1568
1712
|
|
|
1569
1713
|
controller.enqueue({
|
|
1570
|
-
type: 'tool-
|
|
1571
|
-
toolCallId: value.item.
|
|
1572
|
-
toolName
|
|
1573
|
-
|
|
1574
|
-
|
|
1575
|
-
|
|
1714
|
+
type: 'tool-call',
|
|
1715
|
+
toolCallId: value.item.call_id,
|
|
1716
|
+
toolName,
|
|
1717
|
+
input,
|
|
1718
|
+
providerMetadata: {
|
|
1719
|
+
[providerOptionsName]: {
|
|
1720
|
+
itemId: value.item.id,
|
|
1721
|
+
},
|
|
1576
1722
|
},
|
|
1577
1723
|
});
|
|
1578
1724
|
} else if (value.item.type === 'file_search_call') {
|
|
@@ -62,6 +62,7 @@ export async function prepareResponsesTools({
|
|
|
62
62
|
| { type: 'mcp' }
|
|
63
63
|
| { type: 'image_generation' }
|
|
64
64
|
| { type: 'apply_patch' }
|
|
65
|
+
| { type: 'computer' }
|
|
65
66
|
| {
|
|
66
67
|
type: 'allowed_tools';
|
|
67
68
|
mode: 'auto' | 'required';
|
|
@@ -171,6 +172,12 @@ export async function prepareResponsesTools({
|
|
|
171
172
|
});
|
|
172
173
|
break;
|
|
173
174
|
}
|
|
175
|
+
case 'openai.computer': {
|
|
176
|
+
openaiTools.push({
|
|
177
|
+
type: 'computer',
|
|
178
|
+
});
|
|
179
|
+
break;
|
|
180
|
+
}
|
|
174
181
|
case 'openai.web_search_preview': {
|
|
175
182
|
const args = await validateTypes({
|
|
176
183
|
value: tool.args,
|
|
@@ -374,7 +381,8 @@ export async function prepareResponsesTools({
|
|
|
374
381
|
resolvedToolName === 'web_search_preview' ||
|
|
375
382
|
resolvedToolName === 'web_search' ||
|
|
376
383
|
resolvedToolName === 'mcp' ||
|
|
377
|
-
resolvedToolName === 'apply_patch'
|
|
384
|
+
resolvedToolName === 'apply_patch' ||
|
|
385
|
+
resolvedToolName === 'computer'
|
|
378
386
|
? { type: resolvedToolName }
|
|
379
387
|
: resolvedCustomProviderToolNames.has(resolvedToolName)
|
|
380
388
|
? { type: 'custom', name: resolvedToolName }
|
|
@@ -0,0 +1,147 @@
|
|
|
1
|
+
import {
|
|
2
|
+
createProviderDefinedToolFactoryWithOutputSchema,
|
|
3
|
+
lazySchema,
|
|
4
|
+
zodSchema,
|
|
5
|
+
} from '@ai-sdk/provider-utils';
|
|
6
|
+
import { z } from 'zod/v4';
|
|
7
|
+
|
|
8
|
+
const safetyCheckSchema = z.object({
|
|
9
|
+
id: z.string(),
|
|
10
|
+
code: z.string().optional(),
|
|
11
|
+
message: z.string().optional(),
|
|
12
|
+
});
|
|
13
|
+
|
|
14
|
+
const computerActionSchema = z.discriminatedUnion('type', [
|
|
15
|
+
z.object({
|
|
16
|
+
type: z.literal('click'),
|
|
17
|
+
button: z.enum(['left', 'right', 'wheel', 'back', 'forward']),
|
|
18
|
+
x: z.number(),
|
|
19
|
+
y: z.number(),
|
|
20
|
+
keys: z.array(z.string()).optional(),
|
|
21
|
+
}),
|
|
22
|
+
z.object({
|
|
23
|
+
type: z.literal('double_click'),
|
|
24
|
+
x: z.number(),
|
|
25
|
+
y: z.number(),
|
|
26
|
+
keys: z.array(z.string()).optional(),
|
|
27
|
+
}),
|
|
28
|
+
z.object({
|
|
29
|
+
type: z.literal('drag'),
|
|
30
|
+
path: z.array(z.object({ x: z.number(), y: z.number() })),
|
|
31
|
+
keys: z.array(z.string()).optional(),
|
|
32
|
+
}),
|
|
33
|
+
z.object({
|
|
34
|
+
type: z.literal('keypress'),
|
|
35
|
+
keys: z.array(z.string()),
|
|
36
|
+
}),
|
|
37
|
+
z.object({
|
|
38
|
+
type: z.literal('move'),
|
|
39
|
+
x: z.number(),
|
|
40
|
+
y: z.number(),
|
|
41
|
+
keys: z.array(z.string()).optional(),
|
|
42
|
+
}),
|
|
43
|
+
z.object({
|
|
44
|
+
type: z.literal('screenshot'),
|
|
45
|
+
}),
|
|
46
|
+
z.object({
|
|
47
|
+
type: z.literal('scroll'),
|
|
48
|
+
x: z.number(),
|
|
49
|
+
y: z.number(),
|
|
50
|
+
scrollX: z.number(),
|
|
51
|
+
scrollY: z.number(),
|
|
52
|
+
keys: z.array(z.string()).optional(),
|
|
53
|
+
}),
|
|
54
|
+
z.object({
|
|
55
|
+
type: z.literal('type'),
|
|
56
|
+
text: z.string(),
|
|
57
|
+
}),
|
|
58
|
+
z.object({
|
|
59
|
+
type: z.literal('wait'),
|
|
60
|
+
}),
|
|
61
|
+
]);
|
|
62
|
+
|
|
63
|
+
export const computerInputSchema = lazySchema(() =>
|
|
64
|
+
zodSchema(
|
|
65
|
+
z.object({
|
|
66
|
+
actions: z.array(computerActionSchema),
|
|
67
|
+
pendingSafetyChecks: z.array(safetyCheckSchema),
|
|
68
|
+
status: z.enum(['in_progress', 'completed', 'incomplete']),
|
|
69
|
+
}),
|
|
70
|
+
),
|
|
71
|
+
);
|
|
72
|
+
|
|
73
|
+
export const computerOutputSchema = lazySchema(() =>
|
|
74
|
+
zodSchema(
|
|
75
|
+
z.object({
|
|
76
|
+
output: z.union([
|
|
77
|
+
z.object({
|
|
78
|
+
type: z.literal('computer_screenshot'),
|
|
79
|
+
imageUrl: z.string(),
|
|
80
|
+
fileId: z.string().optional(),
|
|
81
|
+
detail: z.enum(['auto', 'low', 'high', 'original']).optional(),
|
|
82
|
+
}),
|
|
83
|
+
z.object({
|
|
84
|
+
type: z.literal('computer_screenshot'),
|
|
85
|
+
fileId: z.string(),
|
|
86
|
+
imageUrl: z.string().optional(),
|
|
87
|
+
detail: z.enum(['auto', 'low', 'high', 'original']).optional(),
|
|
88
|
+
}),
|
|
89
|
+
]),
|
|
90
|
+
acknowledgedSafetyChecks: z.array(safetyCheckSchema).optional(),
|
|
91
|
+
}),
|
|
92
|
+
),
|
|
93
|
+
);
|
|
94
|
+
|
|
95
|
+
export type OpenAIComputerAction = z.infer<typeof computerActionSchema>;
|
|
96
|
+
export type OpenAIComputerSafetyCheck = z.infer<typeof safetyCheckSchema>;
|
|
97
|
+
|
|
98
|
+
const computerToolFactory = createProviderDefinedToolFactoryWithOutputSchema<
|
|
99
|
+
{
|
|
100
|
+
/**
|
|
101
|
+
* Ordered UI actions to execute.
|
|
102
|
+
*/
|
|
103
|
+
actions: OpenAIComputerAction[];
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* Safety checks that must be acknowledged before continuing.
|
|
107
|
+
*/
|
|
108
|
+
pendingSafetyChecks: OpenAIComputerSafetyCheck[];
|
|
109
|
+
|
|
110
|
+
/**
|
|
111
|
+
* Status of the computer call.
|
|
112
|
+
*/
|
|
113
|
+
status: 'in_progress' | 'completed' | 'incomplete';
|
|
114
|
+
},
|
|
115
|
+
{
|
|
116
|
+
/**
|
|
117
|
+
* The screenshot captured after executing all actions.
|
|
118
|
+
*/
|
|
119
|
+
output:
|
|
120
|
+
| {
|
|
121
|
+
type: 'computer_screenshot';
|
|
122
|
+
imageUrl: string;
|
|
123
|
+
fileId?: string;
|
|
124
|
+
detail?: 'auto' | 'low' | 'high' | 'original';
|
|
125
|
+
}
|
|
126
|
+
| {
|
|
127
|
+
type: 'computer_screenshot';
|
|
128
|
+
fileId: string;
|
|
129
|
+
imageUrl?: string;
|
|
130
|
+
detail?: 'auto' | 'low' | 'high' | 'original';
|
|
131
|
+
};
|
|
132
|
+
|
|
133
|
+
/**
|
|
134
|
+
* Safety checks that the application has reviewed and acknowledged.
|
|
135
|
+
*/
|
|
136
|
+
acknowledgedSafetyChecks?: OpenAIComputerSafetyCheck[];
|
|
137
|
+
},
|
|
138
|
+
{}
|
|
139
|
+
>({
|
|
140
|
+
id: 'openai.computer',
|
|
141
|
+
inputSchema: computerInputSchema,
|
|
142
|
+
outputSchema: computerOutputSchema,
|
|
143
|
+
});
|
|
144
|
+
|
|
145
|
+
export const computer = (
|
|
146
|
+
options: Parameters<typeof computerToolFactory>[0] = {},
|
|
147
|
+
) => computerToolFactory(options);
|