ai 7.0.151 → 7.0.153
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 +18 -0
- package/dist/index.js +42 -25
- package/dist/index.js.map +1 -1
- package/dist/internal/index.js +1 -1
- package/package.json +12 -12
- package/src/generate-object/generate-object.ts +1 -1
- package/src/generate-text/generate-text.ts +7 -1
- package/src/middleware/extract-json-middleware.ts +8 -2
- package/src/middleware/extract-reasoning-middleware.ts +42 -30
package/dist/internal/index.js
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "ai",
|
|
3
|
-
"version": "7.0.
|
|
3
|
+
"version": "7.0.153",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "AI SDK by Vercel - build apps like ChatGPT, Claude, Gemini, and more with a single interface for any model using the Vercel AI Gateway or go direct to OpenAI, Anthropic, Google, or any other model provider.",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -42,20 +42,20 @@
|
|
|
42
42
|
}
|
|
43
43
|
},
|
|
44
44
|
"dependencies": {
|
|
45
|
-
"@ai-sdk/gateway": "4.0.
|
|
46
|
-
"@ai-sdk/provider": "4.0.
|
|
47
|
-
"@ai-sdk/provider-utils": "5.0.
|
|
45
|
+
"@ai-sdk/gateway": "4.0.126",
|
|
46
|
+
"@ai-sdk/provider": "4.0.34",
|
|
47
|
+
"@ai-sdk/provider-utils": "5.0.68"
|
|
48
48
|
},
|
|
49
49
|
"devDependencies": {
|
|
50
|
-
"@ai-sdk/amazon-bedrock": "5.0.
|
|
51
|
-
"@ai-sdk/deepseek": "3.0.
|
|
52
|
-
"@ai-sdk/google": "4.0.
|
|
53
|
-
"@ai-sdk/groq": "4.0.
|
|
54
|
-
"@ai-sdk/huggingface": "2.0.
|
|
55
|
-
"@ai-sdk/moonshotai": "3.0.
|
|
56
|
-
"@ai-sdk/openai": "4.0.
|
|
50
|
+
"@ai-sdk/amazon-bedrock": "5.0.124",
|
|
51
|
+
"@ai-sdk/deepseek": "3.0.73",
|
|
52
|
+
"@ai-sdk/google": "4.0.105",
|
|
53
|
+
"@ai-sdk/groq": "4.0.70",
|
|
54
|
+
"@ai-sdk/huggingface": "2.0.78",
|
|
55
|
+
"@ai-sdk/moonshotai": "3.0.78",
|
|
56
|
+
"@ai-sdk/openai": "4.0.102",
|
|
57
57
|
"@ai-sdk/test-server": "2.0.4",
|
|
58
|
-
"@ai-sdk/xai": "5.0.
|
|
58
|
+
"@ai-sdk/xai": "5.0.30",
|
|
59
59
|
"@edge-runtime/vm": "^5.0.0",
|
|
60
60
|
"@smithy/eventstream-codec": "^4.3.3",
|
|
61
61
|
"@smithy/util-utf8": "^4.3.3",
|
|
@@ -1631,8 +1631,14 @@ export async function generateText<
|
|
|
1631
1631
|
(lastStep.finishReason !== 'tool-calls' && lastStep.text.length > 0)
|
|
1632
1632
|
) {
|
|
1633
1633
|
const outputSpecification = output ?? text();
|
|
1634
|
+
// Select the structured output without changing the complete response
|
|
1635
|
+
// content, text, or messages exposed to callers.
|
|
1636
|
+
const textForOutput =
|
|
1637
|
+
(await outputSpecification.responseFormat)?.type === 'json'
|
|
1638
|
+
? (currentModelResponse!.structuredOutputText ?? lastStep.text)
|
|
1639
|
+
: lastStep.text;
|
|
1634
1640
|
resolvedOutput = await outputSpecification.parseCompleteOutput(
|
|
1635
|
-
{ text:
|
|
1641
|
+
{ text: textForOutput },
|
|
1636
1642
|
{
|
|
1637
1643
|
response: lastStep.response,
|
|
1638
1644
|
usage: lastStep.usage,
|
|
@@ -67,7 +67,7 @@ export function extractJsonMiddleware(options?: {
|
|
|
67
67
|
specificationVersion: 'v4',
|
|
68
68
|
|
|
69
69
|
wrapGenerate: async ({ doGenerate }) => {
|
|
70
|
-
const { content, ...rest } = await doGenerate();
|
|
70
|
+
const { content, structuredOutputText, ...rest } = await doGenerate();
|
|
71
71
|
|
|
72
72
|
const transformedContent: LanguageModelV4Content[] = [];
|
|
73
73
|
for (const part of content) {
|
|
@@ -82,7 +82,13 @@ export function extractJsonMiddleware(options?: {
|
|
|
82
82
|
});
|
|
83
83
|
}
|
|
84
84
|
|
|
85
|
-
return {
|
|
85
|
+
return {
|
|
86
|
+
content: transformedContent,
|
|
87
|
+
...rest,
|
|
88
|
+
...(structuredOutputText != null && {
|
|
89
|
+
structuredOutputText: transform(structuredOutputText),
|
|
90
|
+
}),
|
|
91
|
+
};
|
|
86
92
|
},
|
|
87
93
|
wrapStream: async ({ doStream }) => {
|
|
88
94
|
const { stream, ...rest } = await doStream();
|
|
@@ -42,10 +42,40 @@ export function extractReasoningMiddleware({
|
|
|
42
42
|
const escapedOpeningTag = openingTag.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
|
|
43
43
|
const escapedClosingTag = closingTag.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
|
|
44
44
|
|
|
45
|
+
function extractReasoning(input: string) {
|
|
46
|
+
const text = startWithReasoning ? openingTag + input : input;
|
|
47
|
+
const regexp = new RegExp(
|
|
48
|
+
`${escapedOpeningTag}(.*?)${escapedClosingTag}`,
|
|
49
|
+
'gs',
|
|
50
|
+
);
|
|
51
|
+
const matches = Array.from(text.matchAll(regexp));
|
|
52
|
+
|
|
53
|
+
if (!matches.length) {
|
|
54
|
+
return { text: input, reasoning: undefined };
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
const reasoning = matches.map(match => match[1]).join(separator);
|
|
58
|
+
let textWithoutReasoning = text;
|
|
59
|
+
for (let i = matches.length - 1; i >= 0; i--) {
|
|
60
|
+
const match = matches[i];
|
|
61
|
+
const beforeMatch = textWithoutReasoning.slice(0, match.index);
|
|
62
|
+
const afterMatch = textWithoutReasoning.slice(
|
|
63
|
+
match.index! + match[0].length,
|
|
64
|
+
);
|
|
65
|
+
|
|
66
|
+
textWithoutReasoning =
|
|
67
|
+
beforeMatch +
|
|
68
|
+
(beforeMatch.length > 0 && afterMatch.length > 0 ? separator : '') +
|
|
69
|
+
afterMatch;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
return { text: textWithoutReasoning, reasoning };
|
|
73
|
+
}
|
|
74
|
+
|
|
45
75
|
return {
|
|
46
76
|
specificationVersion: 'v4',
|
|
47
77
|
wrapGenerate: async ({ doGenerate }) => {
|
|
48
|
-
const { content, ...rest } = await doGenerate();
|
|
78
|
+
const { content, structuredOutputText, ...rest } = await doGenerate();
|
|
49
79
|
|
|
50
80
|
const transformedContent: LanguageModelV4Content[] = [];
|
|
51
81
|
for (const part of content) {
|
|
@@ -54,48 +84,30 @@ export function extractReasoningMiddleware({
|
|
|
54
84
|
continue;
|
|
55
85
|
}
|
|
56
86
|
|
|
57
|
-
const text
|
|
58
|
-
|
|
59
|
-
const regexp = new RegExp(
|
|
60
|
-
`${escapedOpeningTag}(.*?)${escapedClosingTag}`,
|
|
61
|
-
'gs',
|
|
62
|
-
);
|
|
63
|
-
const matches = Array.from(text.matchAll(regexp));
|
|
64
|
-
|
|
65
|
-
if (!matches.length) {
|
|
87
|
+
const { text, reasoning } = extractReasoning(part.text);
|
|
88
|
+
if (reasoning === undefined) {
|
|
66
89
|
transformedContent.push(part);
|
|
67
90
|
continue;
|
|
68
91
|
}
|
|
69
92
|
|
|
70
|
-
const reasoningText = matches.map(match => match[1]).join(separator);
|
|
71
|
-
|
|
72
|
-
let textWithoutReasoning = text;
|
|
73
|
-
for (let i = matches.length - 1; i >= 0; i--) {
|
|
74
|
-
const match = matches[i];
|
|
75
|
-
|
|
76
|
-
const beforeMatch = textWithoutReasoning.slice(0, match.index);
|
|
77
|
-
const afterMatch = textWithoutReasoning.slice(
|
|
78
|
-
match.index! + match[0].length,
|
|
79
|
-
);
|
|
80
|
-
|
|
81
|
-
textWithoutReasoning =
|
|
82
|
-
beforeMatch +
|
|
83
|
-
(beforeMatch.length > 0 && afterMatch.length > 0 ? separator : '') +
|
|
84
|
-
afterMatch;
|
|
85
|
-
}
|
|
86
|
-
|
|
87
93
|
transformedContent.push({
|
|
88
94
|
type: 'reasoning',
|
|
89
|
-
text:
|
|
95
|
+
text: reasoning,
|
|
90
96
|
});
|
|
91
97
|
|
|
92
98
|
transformedContent.push({
|
|
93
99
|
type: 'text',
|
|
94
|
-
text
|
|
100
|
+
text,
|
|
95
101
|
});
|
|
96
102
|
}
|
|
97
103
|
|
|
98
|
-
return {
|
|
104
|
+
return {
|
|
105
|
+
content: transformedContent,
|
|
106
|
+
...rest,
|
|
107
|
+
...(structuredOutputText != null && {
|
|
108
|
+
structuredOutputText: extractReasoning(structuredOutputText).text,
|
|
109
|
+
}),
|
|
110
|
+
};
|
|
99
111
|
},
|
|
100
112
|
|
|
101
113
|
wrapStream: async ({ doStream }) => {
|