@fondation-io/ai 7.0.0-beta.45
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 +7687 -0
- package/README.md +238 -0
- package/dist/index.d.mts +7056 -0
- package/dist/index.d.ts +7056 -0
- package/dist/index.js +14607 -0
- package/dist/index.js.map +1 -0
- package/dist/index.mjs +14578 -0
- package/dist/index.mjs.map +1 -0
- package/dist/internal/index.d.mts +303 -0
- package/dist/internal/index.d.ts +303 -0
- package/dist/internal/index.js +1352 -0
- package/dist/internal/index.js.map +1 -0
- package/dist/internal/index.mjs +1336 -0
- package/dist/internal/index.mjs.map +1 -0
- package/dist/test/index.d.mts +265 -0
- package/dist/test/index.d.ts +265 -0
- package/dist/test/index.js +509 -0
- package/dist/test/index.js.map +1 -0
- package/dist/test/index.mjs +472 -0
- package/dist/test/index.mjs.map +1 -0
- package/docs/00-introduction/index.mdx +76 -0
- package/docs/02-foundations/01-overview.mdx +43 -0
- package/docs/02-foundations/02-providers-and-models.mdx +160 -0
- package/docs/02-foundations/03-prompts.mdx +616 -0
- package/docs/02-foundations/04-tools.mdx +251 -0
- package/docs/02-foundations/05-streaming.mdx +62 -0
- package/docs/02-foundations/06-provider-options.mdx +345 -0
- package/docs/02-foundations/index.mdx +49 -0
- package/docs/02-getting-started/00-choosing-a-provider.mdx +110 -0
- package/docs/02-getting-started/01-navigating-the-library.mdx +85 -0
- package/docs/02-getting-started/02-nextjs-app-router.mdx +559 -0
- package/docs/02-getting-started/03-nextjs-pages-router.mdx +542 -0
- package/docs/02-getting-started/04-svelte.mdx +627 -0
- package/docs/02-getting-started/05-nuxt.mdx +566 -0
- package/docs/02-getting-started/06-nodejs.mdx +512 -0
- package/docs/02-getting-started/07-expo.mdx +766 -0
- package/docs/02-getting-started/08-tanstack-start.mdx +583 -0
- package/docs/02-getting-started/09-coding-agents.mdx +179 -0
- package/docs/02-getting-started/index.mdx +44 -0
- package/docs/03-agents/01-overview.mdx +96 -0
- package/docs/03-agents/02-building-agents.mdx +449 -0
- package/docs/03-agents/03-workflows.mdx +386 -0
- package/docs/03-agents/04-loop-control.mdx +394 -0
- package/docs/03-agents/05-configuring-call-options.mdx +286 -0
- package/docs/03-agents/06-memory.mdx +222 -0
- package/docs/03-agents/06-subagents.mdx +362 -0
- package/docs/03-agents/index.mdx +46 -0
- package/docs/03-ai-sdk-core/01-overview.mdx +31 -0
- package/docs/03-ai-sdk-core/05-generating-text.mdx +707 -0
- package/docs/03-ai-sdk-core/10-generating-structured-data.mdx +498 -0
- package/docs/03-ai-sdk-core/15-tools-and-tool-calling.mdx +1148 -0
- package/docs/03-ai-sdk-core/16-mcp-tools.mdx +383 -0
- package/docs/03-ai-sdk-core/20-prompt-engineering.mdx +146 -0
- package/docs/03-ai-sdk-core/25-settings.mdx +216 -0
- package/docs/03-ai-sdk-core/26-reasoning.mdx +190 -0
- package/docs/03-ai-sdk-core/30-embeddings.mdx +236 -0
- package/docs/03-ai-sdk-core/31-reranking.mdx +218 -0
- package/docs/03-ai-sdk-core/35-image-generation.mdx +341 -0
- package/docs/03-ai-sdk-core/36-transcription.mdx +227 -0
- package/docs/03-ai-sdk-core/37-speech.mdx +169 -0
- package/docs/03-ai-sdk-core/38-video-generation.mdx +366 -0
- package/docs/03-ai-sdk-core/40-middleware.mdx +485 -0
- package/docs/03-ai-sdk-core/45-provider-management.mdx +349 -0
- package/docs/03-ai-sdk-core/50-error-handling.mdx +149 -0
- package/docs/03-ai-sdk-core/55-testing.mdx +219 -0
- package/docs/03-ai-sdk-core/60-telemetry.mdx +391 -0
- package/docs/03-ai-sdk-core/65-devtools.mdx +107 -0
- package/docs/03-ai-sdk-core/65-event-listeners.mdx +1303 -0
- package/docs/03-ai-sdk-core/index.mdx +99 -0
- package/docs/04-ai-sdk-ui/01-overview.mdx +44 -0
- package/docs/04-ai-sdk-ui/02-chatbot.mdx +1320 -0
- package/docs/04-ai-sdk-ui/03-chatbot-message-persistence.mdx +534 -0
- package/docs/04-ai-sdk-ui/03-chatbot-resume-streams.mdx +263 -0
- package/docs/04-ai-sdk-ui/03-chatbot-tool-usage.mdx +682 -0
- package/docs/04-ai-sdk-ui/04-generative-user-interfaces.mdx +389 -0
- package/docs/04-ai-sdk-ui/05-completion.mdx +181 -0
- package/docs/04-ai-sdk-ui/08-object-generation.mdx +344 -0
- package/docs/04-ai-sdk-ui/20-streaming-data.mdx +397 -0
- package/docs/04-ai-sdk-ui/21-error-handling.mdx +190 -0
- package/docs/04-ai-sdk-ui/21-transport.mdx +174 -0
- package/docs/04-ai-sdk-ui/24-reading-ui-message-streams.mdx +104 -0
- package/docs/04-ai-sdk-ui/25-message-metadata.mdx +152 -0
- package/docs/04-ai-sdk-ui/50-stream-protocol.mdx +503 -0
- package/docs/04-ai-sdk-ui/index.mdx +64 -0
- package/docs/05-ai-sdk-rsc/01-overview.mdx +45 -0
- package/docs/05-ai-sdk-rsc/02-streaming-react-components.mdx +209 -0
- package/docs/05-ai-sdk-rsc/03-generative-ui-state.mdx +279 -0
- package/docs/05-ai-sdk-rsc/03-saving-and-restoring-states.mdx +105 -0
- package/docs/05-ai-sdk-rsc/04-multistep-interfaces.mdx +282 -0
- package/docs/05-ai-sdk-rsc/05-streaming-values.mdx +157 -0
- package/docs/05-ai-sdk-rsc/06-loading-state.mdx +273 -0
- package/docs/05-ai-sdk-rsc/08-error-handling.mdx +94 -0
- package/docs/05-ai-sdk-rsc/09-authentication.mdx +42 -0
- package/docs/05-ai-sdk-rsc/10-migrating-to-ui.mdx +722 -0
- package/docs/05-ai-sdk-rsc/index.mdx +63 -0
- package/docs/06-advanced/01-prompt-engineering.mdx +96 -0
- package/docs/06-advanced/02-stopping-streams.mdx +184 -0
- package/docs/06-advanced/03-backpressure.mdx +173 -0
- package/docs/06-advanced/04-caching.mdx +169 -0
- package/docs/06-advanced/05-multiple-streamables.mdx +68 -0
- package/docs/06-advanced/06-rate-limiting.mdx +60 -0
- package/docs/06-advanced/07-rendering-ui-with-language-models.mdx +225 -0
- package/docs/06-advanced/08-model-as-router.mdx +120 -0
- package/docs/06-advanced/09-multistep-interfaces.mdx +115 -0
- package/docs/06-advanced/09-sequential-generations.mdx +55 -0
- package/docs/06-advanced/10-vercel-deployment-guide.mdx +117 -0
- package/docs/06-advanced/index.mdx +11 -0
- package/docs/07-reference/01-ai-sdk-core/01-generate-text.mdx +2785 -0
- package/docs/07-reference/01-ai-sdk-core/02-stream-text.mdx +3752 -0
- package/docs/07-reference/01-ai-sdk-core/05-embed.mdx +332 -0
- package/docs/07-reference/01-ai-sdk-core/06-embed-many.mdx +330 -0
- package/docs/07-reference/01-ai-sdk-core/06-rerank.mdx +323 -0
- package/docs/07-reference/01-ai-sdk-core/10-generate-image.mdx +251 -0
- package/docs/07-reference/01-ai-sdk-core/11-transcribe.mdx +152 -0
- package/docs/07-reference/01-ai-sdk-core/12-generate-speech.mdx +221 -0
- package/docs/07-reference/01-ai-sdk-core/13-generate-video.mdx +264 -0
- package/docs/07-reference/01-ai-sdk-core/15-agent.mdx +235 -0
- package/docs/07-reference/01-ai-sdk-core/16-tool-loop-agent.mdx +973 -0
- package/docs/07-reference/01-ai-sdk-core/17-create-agent-ui-stream.mdx +154 -0
- package/docs/07-reference/01-ai-sdk-core/18-create-agent-ui-stream-response.mdx +173 -0
- package/docs/07-reference/01-ai-sdk-core/18-pipe-agent-ui-stream-to-response.mdx +150 -0
- package/docs/07-reference/01-ai-sdk-core/20-tool.mdx +209 -0
- package/docs/07-reference/01-ai-sdk-core/22-dynamic-tool.mdx +223 -0
- package/docs/07-reference/01-ai-sdk-core/23-create-mcp-client.mdx +423 -0
- package/docs/07-reference/01-ai-sdk-core/24-mcp-stdio-transport.mdx +68 -0
- package/docs/07-reference/01-ai-sdk-core/25-json-schema.mdx +94 -0
- package/docs/07-reference/01-ai-sdk-core/26-zod-schema.mdx +109 -0
- package/docs/07-reference/01-ai-sdk-core/27-valibot-schema.mdx +58 -0
- package/docs/07-reference/01-ai-sdk-core/28-output.mdx +342 -0
- package/docs/07-reference/01-ai-sdk-core/30-model-message.mdx +435 -0
- package/docs/07-reference/01-ai-sdk-core/31-ui-message.mdx +264 -0
- package/docs/07-reference/01-ai-sdk-core/32-validate-ui-messages.mdx +101 -0
- package/docs/07-reference/01-ai-sdk-core/33-safe-validate-ui-messages.mdx +113 -0
- package/docs/07-reference/01-ai-sdk-core/40-provider-registry.mdx +198 -0
- package/docs/07-reference/01-ai-sdk-core/42-custom-provider.mdx +157 -0
- package/docs/07-reference/01-ai-sdk-core/50-cosine-similarity.mdx +52 -0
- package/docs/07-reference/01-ai-sdk-core/60-wrap-language-model.mdx +59 -0
- package/docs/07-reference/01-ai-sdk-core/61-wrap-image-model.mdx +64 -0
- package/docs/07-reference/01-ai-sdk-core/65-language-model-v2-middleware.mdx +74 -0
- package/docs/07-reference/01-ai-sdk-core/66-extract-reasoning-middleware.mdx +68 -0
- package/docs/07-reference/01-ai-sdk-core/67-simulate-streaming-middleware.mdx +71 -0
- package/docs/07-reference/01-ai-sdk-core/68-default-settings-middleware.mdx +80 -0
- package/docs/07-reference/01-ai-sdk-core/69-add-tool-input-examples-middleware.mdx +155 -0
- package/docs/07-reference/01-ai-sdk-core/70-extract-json-middleware.mdx +147 -0
- package/docs/07-reference/01-ai-sdk-core/70-step-count-is.mdx +84 -0
- package/docs/07-reference/01-ai-sdk-core/71-has-tool-call.mdx +120 -0
- package/docs/07-reference/01-ai-sdk-core/75-simulate-readable-stream.mdx +94 -0
- package/docs/07-reference/01-ai-sdk-core/80-smooth-stream.mdx +145 -0
- package/docs/07-reference/01-ai-sdk-core/90-generate-id.mdx +30 -0
- package/docs/07-reference/01-ai-sdk-core/91-create-id-generator.mdx +89 -0
- package/docs/07-reference/01-ai-sdk-core/92-default-generated-file.mdx +68 -0
- package/docs/07-reference/01-ai-sdk-core/index.mdx +160 -0
- package/docs/07-reference/02-ai-sdk-ui/01-use-chat.mdx +493 -0
- package/docs/07-reference/02-ai-sdk-ui/02-use-completion.mdx +185 -0
- package/docs/07-reference/02-ai-sdk-ui/03-use-object.mdx +196 -0
- package/docs/07-reference/02-ai-sdk-ui/31-convert-to-model-messages.mdx +231 -0
- package/docs/07-reference/02-ai-sdk-ui/32-prune-messages.mdx +108 -0
- package/docs/07-reference/02-ai-sdk-ui/40-create-ui-message-stream.mdx +162 -0
- package/docs/07-reference/02-ai-sdk-ui/41-create-ui-message-stream-response.mdx +119 -0
- package/docs/07-reference/02-ai-sdk-ui/42-pipe-ui-message-stream-to-response.mdx +77 -0
- package/docs/07-reference/02-ai-sdk-ui/43-read-ui-message-stream.mdx +57 -0
- package/docs/07-reference/02-ai-sdk-ui/46-infer-ui-tools.mdx +99 -0
- package/docs/07-reference/02-ai-sdk-ui/47-infer-ui-tool.mdx +75 -0
- package/docs/07-reference/02-ai-sdk-ui/50-direct-chat-transport.mdx +333 -0
- package/docs/07-reference/02-ai-sdk-ui/index.mdx +89 -0
- package/docs/07-reference/03-ai-sdk-rsc/01-stream-ui.mdx +767 -0
- package/docs/07-reference/03-ai-sdk-rsc/02-create-ai.mdx +90 -0
- package/docs/07-reference/03-ai-sdk-rsc/03-create-streamable-ui.mdx +91 -0
- package/docs/07-reference/03-ai-sdk-rsc/04-create-streamable-value.mdx +78 -0
- package/docs/07-reference/03-ai-sdk-rsc/05-read-streamable-value.mdx +79 -0
- package/docs/07-reference/03-ai-sdk-rsc/06-get-ai-state.mdx +50 -0
- package/docs/07-reference/03-ai-sdk-rsc/07-get-mutable-ai-state.mdx +70 -0
- package/docs/07-reference/03-ai-sdk-rsc/08-use-ai-state.mdx +26 -0
- package/docs/07-reference/03-ai-sdk-rsc/09-use-actions.mdx +42 -0
- package/docs/07-reference/03-ai-sdk-rsc/10-use-ui-state.mdx +35 -0
- package/docs/07-reference/03-ai-sdk-rsc/11-use-streamable-value.mdx +46 -0
- package/docs/07-reference/03-ai-sdk-rsc/20-render.mdx +266 -0
- package/docs/07-reference/03-ai-sdk-rsc/index.mdx +67 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-api-call-error.mdx +31 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-download-error.mdx +28 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-empty-response-body-error.mdx +24 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-invalid-argument-error.mdx +26 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-invalid-data-content-error.mdx +26 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-invalid-message-role-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-invalid-prompt-error.mdx +47 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-invalid-response-data-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-invalid-tool-approval-error.mdx +24 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-invalid-tool-input-error.mdx +27 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-json-parse-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-load-api-key-error.mdx +24 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-load-setting-error.mdx +24 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-message-conversion-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-content-generated-error.mdx +24 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-image-generated-error.mdx +36 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-object-generated-error.mdx +43 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-output-generated-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-speech-generated-error.mdx +24 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-such-model-error.mdx +26 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-such-provider-error.mdx +28 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-such-tool-error.mdx +26 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-transcript-generated-error.mdx +24 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-no-video-generated-error.mdx +39 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-retry-error.mdx +27 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-too-many-embedding-values-for-call-error.mdx +27 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-tool-call-not-found-for-approval-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-tool-call-repair-error.mdx +28 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-type-validation-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-ui-message-stream-error.mdx +67 -0
- package/docs/07-reference/05-ai-sdk-errors/ai-unsupported-functionality-error.mdx +25 -0
- package/docs/07-reference/05-ai-sdk-errors/index.mdx +39 -0
- package/docs/07-reference/index.mdx +28 -0
- package/docs/08-migration-guides/00-versioning.mdx +46 -0
- package/docs/08-migration-guides/23-migration-guide-7-0.mdx +95 -0
- package/docs/08-migration-guides/24-migration-guide-6-0.mdx +823 -0
- package/docs/08-migration-guides/25-migration-guide-5-0-data.mdx +882 -0
- package/docs/08-migration-guides/26-migration-guide-5-0.mdx +3427 -0
- package/docs/08-migration-guides/27-migration-guide-4-2.mdx +99 -0
- package/docs/08-migration-guides/28-migration-guide-4-1.mdx +14 -0
- package/docs/08-migration-guides/29-migration-guide-4-0.mdx +1157 -0
- package/docs/08-migration-guides/36-migration-guide-3-4.mdx +14 -0
- package/docs/08-migration-guides/37-migration-guide-3-3.mdx +64 -0
- package/docs/08-migration-guides/38-migration-guide-3-2.mdx +46 -0
- package/docs/08-migration-guides/39-migration-guide-3-1.mdx +168 -0
- package/docs/08-migration-guides/index.mdx +22 -0
- package/docs/09-troubleshooting/01-azure-stream-slow.mdx +33 -0
- package/docs/09-troubleshooting/03-server-actions-in-client-components.mdx +40 -0
- package/docs/09-troubleshooting/04-strange-stream-output.mdx +36 -0
- package/docs/09-troubleshooting/05-streamable-ui-errors.mdx +16 -0
- package/docs/09-troubleshooting/05-tool-invocation-missing-result.mdx +106 -0
- package/docs/09-troubleshooting/06-streaming-not-working-when-deployed.mdx +31 -0
- package/docs/09-troubleshooting/06-streaming-not-working-when-proxied.mdx +31 -0
- package/docs/09-troubleshooting/06-timeout-on-vercel.mdx +60 -0
- package/docs/09-troubleshooting/07-unclosed-streams.mdx +34 -0
- package/docs/09-troubleshooting/08-use-chat-failed-to-parse-stream.mdx +26 -0
- package/docs/09-troubleshooting/09-client-stream-error.mdx +25 -0
- package/docs/09-troubleshooting/10-use-chat-tools-no-response.mdx +32 -0
- package/docs/09-troubleshooting/11-use-chat-custom-request-options.mdx +149 -0
- package/docs/09-troubleshooting/12-typescript-performance-zod.mdx +46 -0
- package/docs/09-troubleshooting/12-use-chat-an-error-occurred.mdx +59 -0
- package/docs/09-troubleshooting/13-repeated-assistant-messages.mdx +73 -0
- package/docs/09-troubleshooting/14-stream-abort-handling.mdx +73 -0
- package/docs/09-troubleshooting/14-tool-calling-with-structured-outputs.mdx +48 -0
- package/docs/09-troubleshooting/15-abort-breaks-resumable-streams.mdx +55 -0
- package/docs/09-troubleshooting/15-stream-text-not-working.mdx +33 -0
- package/docs/09-troubleshooting/16-streaming-status-delay.mdx +63 -0
- package/docs/09-troubleshooting/17-use-chat-stale-body-data.mdx +141 -0
- package/docs/09-troubleshooting/18-ontoolcall-type-narrowing.mdx +66 -0
- package/docs/09-troubleshooting/19-unsupported-model-version.mdx +50 -0
- package/docs/09-troubleshooting/20-no-object-generated-content-filter.mdx +76 -0
- package/docs/09-troubleshooting/21-missing-tool-results-error.mdx +82 -0
- package/docs/09-troubleshooting/30-model-is-not-assignable-to-type.mdx +21 -0
- package/docs/09-troubleshooting/40-typescript-cannot-find-namespace-jsx.mdx +24 -0
- package/docs/09-troubleshooting/50-react-maximum-update-depth-exceeded.mdx +39 -0
- package/docs/09-troubleshooting/60-jest-cannot-find-module-ai-rsc.mdx +22 -0
- package/docs/09-troubleshooting/70-high-memory-usage-with-images.mdx +108 -0
- package/docs/09-troubleshooting/index.mdx +11 -0
- package/internal.d.ts +1 -0
- package/package.json +120 -0
- package/src/agent/agent.ts +156 -0
- package/src/agent/create-agent-ui-stream-response.ts +61 -0
- package/src/agent/create-agent-ui-stream.ts +84 -0
- package/src/agent/index.ts +37 -0
- package/src/agent/infer-agent-tools.ts +7 -0
- package/src/agent/infer-agent-ui-message.ts +11 -0
- package/src/agent/pipe-agent-ui-stream-to-response.ts +64 -0
- package/src/agent/tool-loop-agent-settings.ts +252 -0
- package/src/agent/tool-loop-agent.ts +205 -0
- package/src/embed/embed-events.ts +181 -0
- package/src/embed/embed-many-result.ts +53 -0
- package/src/embed/embed-many.ts +428 -0
- package/src/embed/embed-result.ts +50 -0
- package/src/embed/embed.ts +266 -0
- package/src/embed/index.ts +5 -0
- package/src/error/index.ts +37 -0
- package/src/error/invalid-argument-error.ts +34 -0
- package/src/error/invalid-stream-part-error.ts +28 -0
- package/src/error/invalid-tool-approval-error.ts +26 -0
- package/src/error/invalid-tool-input-error.ts +33 -0
- package/src/error/missing-tool-result-error.ts +28 -0
- package/src/error/no-image-generated-error.ts +39 -0
- package/src/error/no-object-generated-error.ts +70 -0
- package/src/error/no-output-generated-error.ts +26 -0
- package/src/error/no-speech-generated-error.ts +28 -0
- package/src/error/no-such-tool-error.ts +35 -0
- package/src/error/no-transcript-generated-error.ts +30 -0
- package/src/error/no-video-generated-error.ts +57 -0
- package/src/error/tool-call-not-found-for-approval-error.ts +32 -0
- package/src/error/tool-call-repair-error.ts +30 -0
- package/src/error/ui-message-stream-error.ts +48 -0
- package/src/error/unsupported-model-version-error.ts +23 -0
- package/src/error/verify-no-object-generated-error.ts +27 -0
- package/src/generate-image/generate-image-result.ts +42 -0
- package/src/generate-image/generate-image.ts +361 -0
- package/src/generate-image/index.ts +18 -0
- package/src/generate-object/generate-object-result.ts +67 -0
- package/src/generate-object/generate-object.ts +514 -0
- package/src/generate-object/index.ts +9 -0
- package/src/generate-object/inject-json-instruction.ts +30 -0
- package/src/generate-object/output-strategy.ts +415 -0
- package/src/generate-object/parse-and-validate-object-result.ts +111 -0
- package/src/generate-object/repair-text.ts +12 -0
- package/src/generate-object/stream-object-result.ts +120 -0
- package/src/generate-object/stream-object.ts +984 -0
- package/src/generate-object/validate-object-generation-input.ts +144 -0
- package/src/generate-speech/generate-speech-result.ts +30 -0
- package/src/generate-speech/generate-speech.ts +191 -0
- package/src/generate-speech/generated-audio-file.ts +65 -0
- package/src/generate-speech/index.ts +3 -0
- package/src/generate-text/collect-tool-approvals.ts +116 -0
- package/src/generate-text/content-part.ts +31 -0
- package/src/generate-text/core-events.ts +390 -0
- package/src/generate-text/create-execute-tools-transformation.ts +144 -0
- package/src/generate-text/execute-tool-call.ts +190 -0
- package/src/generate-text/extract-reasoning-content.ts +17 -0
- package/src/generate-text/extract-text-content.ts +15 -0
- package/src/generate-text/generate-text-result.ts +168 -0
- package/src/generate-text/generate-text.ts +1445 -0
- package/src/generate-text/generated-file.ts +70 -0
- package/src/generate-text/index.ts +78 -0
- package/src/generate-text/invoke-tool-callbacks-from-stream.ts +81 -0
- package/src/generate-text/is-approval-needed.ts +29 -0
- package/src/generate-text/output-utils.ts +23 -0
- package/src/generate-text/output.ts +590 -0
- package/src/generate-text/parse-tool-call.ts +188 -0
- package/src/generate-text/prepare-step.ts +103 -0
- package/src/generate-text/prune-messages.ts +167 -0
- package/src/generate-text/reasoning-output.ts +99 -0
- package/src/generate-text/reasoning.ts +10 -0
- package/src/generate-text/response-message.ts +10 -0
- package/src/generate-text/smooth-stream.ts +162 -0
- package/src/generate-text/step-result.ts +310 -0
- package/src/generate-text/stop-condition.ts +29 -0
- package/src/generate-text/stream-model-call.ts +418 -0
- package/src/generate-text/stream-text-result.ts +536 -0
- package/src/generate-text/stream-text.ts +2696 -0
- package/src/generate-text/to-response-messages.ts +195 -0
- package/src/generate-text/tool-approval-request-output.ts +21 -0
- package/src/generate-text/tool-call-repair-function.ts +27 -0
- package/src/generate-text/tool-call.ts +47 -0
- package/src/generate-text/tool-error.ts +34 -0
- package/src/generate-text/tool-output-denied.ts +21 -0
- package/src/generate-text/tool-output.ts +7 -0
- package/src/generate-text/tool-result.ts +36 -0
- package/src/generate-text/tool-set.ts +14 -0
- package/src/generate-video/generate-video-result.ts +36 -0
- package/src/generate-video/generate-video.ts +402 -0
- package/src/generate-video/index.ts +3 -0
- package/src/global.ts +36 -0
- package/src/index.ts +49 -0
- package/src/logger/index.ts +6 -0
- package/src/logger/log-warnings.ts +140 -0
- package/src/middleware/add-tool-input-examples-middleware.ts +90 -0
- package/src/middleware/default-embedding-settings-middleware.ts +22 -0
- package/src/middleware/default-settings-middleware.ts +33 -0
- package/src/middleware/extract-json-middleware.ts +197 -0
- package/src/middleware/extract-reasoning-middleware.ts +249 -0
- package/src/middleware/index.ts +10 -0
- package/src/middleware/simulate-streaming-middleware.ts +79 -0
- package/src/middleware/wrap-embedding-model.ts +89 -0
- package/src/middleware/wrap-image-model.ts +92 -0
- package/src/middleware/wrap-language-model.ts +108 -0
- package/src/middleware/wrap-provider.ts +51 -0
- package/src/model/as-embedding-model-v3.ts +24 -0
- package/src/model/as-embedding-model-v4.ts +25 -0
- package/src/model/as-image-model-v3.ts +24 -0
- package/src/model/as-image-model-v4.ts +21 -0
- package/src/model/as-language-model-v3.ts +103 -0
- package/src/model/as-language-model-v4.ts +25 -0
- package/src/model/as-provider-v3.ts +36 -0
- package/src/model/as-provider-v4.ts +47 -0
- package/src/model/as-reranking-model-v4.ts +16 -0
- package/src/model/as-speech-model-v3.ts +24 -0
- package/src/model/as-speech-model-v4.ts +21 -0
- package/src/model/as-transcription-model-v3.ts +24 -0
- package/src/model/as-transcription-model-v4.ts +25 -0
- package/src/model/as-video-model-v4.ts +19 -0
- package/src/model/resolve-model.ts +172 -0
- package/src/prompt/call-settings.ts +169 -0
- package/src/prompt/content-part.ts +236 -0
- package/src/prompt/convert-to-language-model-prompt.ts +548 -0
- package/src/prompt/create-tool-model-output.ts +34 -0
- package/src/prompt/data-content.ts +134 -0
- package/src/prompt/index.ts +27 -0
- package/src/prompt/invalid-data-content-error.ts +29 -0
- package/src/prompt/invalid-message-role-error.ts +27 -0
- package/src/prompt/message-conversion-error.ts +28 -0
- package/src/prompt/message.ts +72 -0
- package/src/prompt/prepare-call-settings.ts +110 -0
- package/src/prompt/prepare-tools-and-tool-choice.ts +86 -0
- package/src/prompt/prompt.ts +43 -0
- package/src/prompt/split-data-url.ts +17 -0
- package/src/prompt/standardize-prompt.ts +99 -0
- package/src/prompt/wrap-gateway-error.ts +29 -0
- package/src/registry/custom-provider.ts +210 -0
- package/src/registry/index.ts +7 -0
- package/src/registry/no-such-provider-error.ts +41 -0
- package/src/registry/provider-registry.ts +331 -0
- package/src/rerank/index.ts +8 -0
- package/src/rerank/rerank-events.ts +189 -0
- package/src/rerank/rerank-result.ts +70 -0
- package/src/rerank/rerank.ts +348 -0
- package/src/telemetry/assemble-operation-name.ts +21 -0
- package/src/telemetry/get-base-telemetry-attributes.ts +45 -0
- package/src/telemetry/get-global-telemetry-integration.ts +126 -0
- package/src/telemetry/get-tracer.ts +20 -0
- package/src/telemetry/index.ts +4 -0
- package/src/telemetry/noop-tracer.ts +69 -0
- package/src/telemetry/open-telemetry-integration.ts +875 -0
- package/src/telemetry/record-span.ts +75 -0
- package/src/telemetry/select-telemetry-attributes.ts +78 -0
- package/src/telemetry/stringify-for-telemetry.ts +33 -0
- package/src/telemetry/telemetry-integration-registry.ts +22 -0
- package/src/telemetry/telemetry-integration.ts +139 -0
- package/src/telemetry/telemetry-settings.ts +55 -0
- package/src/test/mock-embedding-model-v2.ts +35 -0
- package/src/test/mock-embedding-model-v3.ts +48 -0
- package/src/test/mock-embedding-model-v4.ts +48 -0
- package/src/test/mock-image-model-v2.ts +28 -0
- package/src/test/mock-image-model-v3.ts +28 -0
- package/src/test/mock-image-model-v4.ts +28 -0
- package/src/test/mock-language-model-v2.ts +72 -0
- package/src/test/mock-language-model-v3.ts +77 -0
- package/src/test/mock-language-model-v4.ts +77 -0
- package/src/test/mock-provider-v2.ts +68 -0
- package/src/test/mock-provider-v3.ts +80 -0
- package/src/test/mock-provider-v4.ts +80 -0
- package/src/test/mock-reranking-model-v3.ts +25 -0
- package/src/test/mock-reranking-model-v4.ts +25 -0
- package/src/test/mock-server-response.ts +69 -0
- package/src/test/mock-speech-model-v2.ts +24 -0
- package/src/test/mock-speech-model-v3.ts +24 -0
- package/src/test/mock-speech-model-v4.ts +24 -0
- package/src/test/mock-tracer.ts +156 -0
- package/src/test/mock-transcription-model-v2.ts +24 -0
- package/src/test/mock-transcription-model-v3.ts +24 -0
- package/src/test/mock-transcription-model-v4.ts +24 -0
- package/src/test/mock-values.ts +4 -0
- package/src/test/mock-video-model-v3.ts +28 -0
- package/src/test/mock-video-model-v4.ts +28 -0
- package/src/test/not-implemented.ts +3 -0
- package/src/text-stream/create-text-stream-response.ts +30 -0
- package/src/text-stream/index.ts +2 -0
- package/src/text-stream/pipe-text-stream-to-response.ts +38 -0
- package/src/transcribe/index.ts +2 -0
- package/src/transcribe/transcribe-result.ts +60 -0
- package/src/transcribe/transcribe.ts +187 -0
- package/src/types/embedding-model-middleware.ts +15 -0
- package/src/types/embedding-model.ts +20 -0
- package/src/types/image-model-middleware.ts +15 -0
- package/src/types/image-model-response-metadata.ts +16 -0
- package/src/types/image-model.ts +19 -0
- package/src/types/index.ts +29 -0
- package/src/types/json-value.ts +15 -0
- package/src/types/language-model-middleware.ts +15 -0
- package/src/types/language-model-request-metadata.ts +6 -0
- package/src/types/language-model-response-metadata.ts +21 -0
- package/src/types/language-model.ts +106 -0
- package/src/types/provider-metadata.ts +16 -0
- package/src/types/provider.ts +55 -0
- package/src/types/reranking-model.ts +6 -0
- package/src/types/speech-model-response-metadata.ts +21 -0
- package/src/types/speech-model.ts +10 -0
- package/src/types/transcription-model-response-metadata.ts +16 -0
- package/src/types/transcription-model.ts +14 -0
- package/src/types/usage.ts +200 -0
- package/src/types/video-model-response-metadata.ts +28 -0
- package/src/types/video-model.ts +15 -0
- package/src/types/warning.ts +7 -0
- package/src/ui/call-completion-api.ts +157 -0
- package/src/ui/chat-transport.ts +83 -0
- package/src/ui/chat.ts +786 -0
- package/src/ui/convert-file-list-to-file-ui-parts.ts +36 -0
- package/src/ui/convert-to-model-messages.ts +403 -0
- package/src/ui/default-chat-transport.ts +36 -0
- package/src/ui/direct-chat-transport.ts +117 -0
- package/src/ui/http-chat-transport.ts +273 -0
- package/src/ui/index.ts +76 -0
- package/src/ui/last-assistant-message-is-complete-with-approval-responses.ts +44 -0
- package/src/ui/last-assistant-message-is-complete-with-tool-calls.ts +39 -0
- package/src/ui/process-text-stream.ts +16 -0
- package/src/ui/process-ui-message-stream.ts +858 -0
- package/src/ui/text-stream-chat-transport.ts +23 -0
- package/src/ui/transform-text-to-ui-message-stream.ts +27 -0
- package/src/ui/ui-messages.ts +602 -0
- package/src/ui/use-completion.ts +84 -0
- package/src/ui/validate-ui-messages.ts +521 -0
- package/src/ui-message-stream/create-ui-message-stream-response.ts +44 -0
- package/src/ui-message-stream/create-ui-message-stream.ts +145 -0
- package/src/ui-message-stream/get-response-ui-message-id.ts +35 -0
- package/src/ui-message-stream/handle-ui-message-stream-finish.ts +170 -0
- package/src/ui-message-stream/index.ts +14 -0
- package/src/ui-message-stream/json-to-sse-transform-stream.ts +17 -0
- package/src/ui-message-stream/pipe-ui-message-stream-to-response.ts +51 -0
- package/src/ui-message-stream/read-ui-message-stream.ts +87 -0
- package/src/ui-message-stream/ui-message-chunks.ts +372 -0
- package/src/ui-message-stream/ui-message-stream-headers.ts +7 -0
- package/src/ui-message-stream/ui-message-stream-on-finish-callback.ts +32 -0
- package/src/ui-message-stream/ui-message-stream-on-step-finish-callback.ts +25 -0
- package/src/ui-message-stream/ui-message-stream-response-init.ts +14 -0
- package/src/ui-message-stream/ui-message-stream-writer.ts +24 -0
- package/src/util/as-array.ts +3 -0
- package/src/util/async-iterable-stream.ts +94 -0
- package/src/util/consume-stream.ts +31 -0
- package/src/util/cosine-similarity.ts +46 -0
- package/src/util/create-resolvable-promise.ts +30 -0
- package/src/util/create-stitchable-stream.ts +112 -0
- package/src/util/data-url.ts +17 -0
- package/src/util/deep-partial.ts +84 -0
- package/src/util/detect-media-type.ts +226 -0
- package/src/util/download/create-download.ts +13 -0
- package/src/util/download/download-function.ts +45 -0
- package/src/util/download/download.ts +74 -0
- package/src/util/error-handler.ts +1 -0
- package/src/util/fix-json.ts +401 -0
- package/src/util/get-potential-start-index.ts +39 -0
- package/src/util/index.ts +12 -0
- package/src/util/is-deep-equal-data.ts +48 -0
- package/src/util/is-non-empty-object.ts +5 -0
- package/src/util/job.ts +1 -0
- package/src/util/log-v2-compatibility-warning.ts +21 -0
- package/src/util/merge-abort-signals.ts +43 -0
- package/src/util/merge-objects.ts +79 -0
- package/src/util/notify.ts +22 -0
- package/src/util/now.ts +4 -0
- package/src/util/parse-partial-json.ts +30 -0
- package/src/util/prepare-headers.ts +14 -0
- package/src/util/prepare-retries.ts +47 -0
- package/src/util/retry-error.ts +41 -0
- package/src/util/retry-with-exponential-backoff.ts +154 -0
- package/src/util/serial-job-executor.ts +36 -0
- package/src/util/simulate-readable-stream.ts +39 -0
- package/src/util/split-array.ts +20 -0
- package/src/util/value-of.ts +65 -0
- package/src/util/write-to-server-response.ts +49 -0
- package/src/version.ts +5 -0
- package/test.d.ts +1 -0
|
@@ -0,0 +1,1445 @@
|
|
|
1
|
+
import {
|
|
2
|
+
LanguageModelV4,
|
|
3
|
+
LanguageModelV4Content,
|
|
4
|
+
LanguageModelV4ToolCall,
|
|
5
|
+
} from '@ai-sdk/provider';
|
|
6
|
+
import {
|
|
7
|
+
createIdGenerator,
|
|
8
|
+
getErrorMessage,
|
|
9
|
+
IdGenerator,
|
|
10
|
+
ProviderOptions,
|
|
11
|
+
ToolApprovalResponse,
|
|
12
|
+
withUserAgentSuffix,
|
|
13
|
+
} from '@ai-sdk/provider-utils';
|
|
14
|
+
import { NoOutputGeneratedError } from '../error';
|
|
15
|
+
import { ToolCallNotFoundForApprovalError } from '../error/tool-call-not-found-for-approval-error';
|
|
16
|
+
import { logWarnings } from '../logger/log-warnings';
|
|
17
|
+
import { resolveLanguageModel } from '../model/resolve-model';
|
|
18
|
+
import { ModelMessage } from '../prompt';
|
|
19
|
+
import {
|
|
20
|
+
CallSettings,
|
|
21
|
+
getStepTimeoutMs,
|
|
22
|
+
getTotalTimeoutMs,
|
|
23
|
+
TimeoutConfiguration,
|
|
24
|
+
} from '../prompt/call-settings';
|
|
25
|
+
import { convertToLanguageModelPrompt } from '../prompt/convert-to-language-model-prompt';
|
|
26
|
+
import { createToolModelOutput } from '../prompt/create-tool-model-output';
|
|
27
|
+
import { prepareCallSettings } from '../prompt/prepare-call-settings';
|
|
28
|
+
import { prepareToolsAndToolChoice } from '../prompt/prepare-tools-and-tool-choice';
|
|
29
|
+
import { Prompt } from '../prompt/prompt';
|
|
30
|
+
import { standardizePrompt } from '../prompt/standardize-prompt';
|
|
31
|
+
import { wrapGatewayError } from '../prompt/wrap-gateway-error';
|
|
32
|
+
import { getGlobalTelemetryIntegration } from '../telemetry/get-global-telemetry-integration';
|
|
33
|
+
import type { TelemetryIntegration } from '../telemetry/telemetry-integration';
|
|
34
|
+
import { TelemetrySettings } from '../telemetry/telemetry-settings';
|
|
35
|
+
import {
|
|
36
|
+
LanguageModel,
|
|
37
|
+
LanguageModelRequestMetadata,
|
|
38
|
+
ToolChoice,
|
|
39
|
+
} from '../types';
|
|
40
|
+
import {
|
|
41
|
+
addLanguageModelUsage,
|
|
42
|
+
asLanguageModelUsage,
|
|
43
|
+
LanguageModelUsage,
|
|
44
|
+
} from '../types/usage';
|
|
45
|
+
import { asArray } from '../util/as-array';
|
|
46
|
+
import { DownloadFunction } from '../util/download/download-function';
|
|
47
|
+
import { mergeAbortSignals } from '../util/merge-abort-signals';
|
|
48
|
+
import { mergeObjects } from '../util/merge-objects';
|
|
49
|
+
import { notify } from '../util/notify';
|
|
50
|
+
import { prepareRetries } from '../util/prepare-retries';
|
|
51
|
+
import { VERSION } from '../version';
|
|
52
|
+
import type {
|
|
53
|
+
OnFinishEvent,
|
|
54
|
+
OnStartEvent,
|
|
55
|
+
OnStepFinishEvent,
|
|
56
|
+
OnStepStartEvent,
|
|
57
|
+
OnToolCallFinishEvent,
|
|
58
|
+
OnToolCallStartEvent,
|
|
59
|
+
} from './core-events';
|
|
60
|
+
import { collectToolApprovals } from './collect-tool-approvals';
|
|
61
|
+
import { ContentPart } from './content-part';
|
|
62
|
+
import { executeToolCall } from './execute-tool-call';
|
|
63
|
+
import { GenerateTextResult } from './generate-text-result';
|
|
64
|
+
import { DefaultGeneratedFile } from './generated-file';
|
|
65
|
+
import { isApprovalNeeded } from './is-approval-needed';
|
|
66
|
+
import { Output, text } from './output';
|
|
67
|
+
import { InferCompleteOutput } from './output-utils';
|
|
68
|
+
import { parseToolCall } from './parse-tool-call';
|
|
69
|
+
import { PrepareStepFunction } from './prepare-step';
|
|
70
|
+
import { convertToReasoningOutputs } from './reasoning-output';
|
|
71
|
+
import { ResponseMessage } from './response-message';
|
|
72
|
+
import { DefaultStepResult, StepResult } from './step-result';
|
|
73
|
+
import {
|
|
74
|
+
isStopConditionMet,
|
|
75
|
+
stepCountIs,
|
|
76
|
+
StopCondition,
|
|
77
|
+
} from './stop-condition';
|
|
78
|
+
import { toResponseMessages } from './to-response-messages';
|
|
79
|
+
import { ToolApprovalRequestOutput } from './tool-approval-request-output';
|
|
80
|
+
import { TypedToolCall } from './tool-call';
|
|
81
|
+
import { ToolCallRepairFunction } from './tool-call-repair-function';
|
|
82
|
+
import { TypedToolError } from './tool-error';
|
|
83
|
+
import { ToolOutput } from './tool-output';
|
|
84
|
+
import { TypedToolResult } from './tool-result';
|
|
85
|
+
import { ToolSet } from './tool-set';
|
|
86
|
+
|
|
87
|
+
const originalGenerateId = createIdGenerator({
|
|
88
|
+
prefix: 'aitxt',
|
|
89
|
+
size: 24,
|
|
90
|
+
});
|
|
91
|
+
|
|
92
|
+
const originalGenerateCallId = createIdGenerator({
|
|
93
|
+
prefix: 'call',
|
|
94
|
+
size: 24,
|
|
95
|
+
});
|
|
96
|
+
|
|
97
|
+
/**
|
|
98
|
+
* Include settings for generateText (requestBody and responseBody).
|
|
99
|
+
*/
|
|
100
|
+
type GenerateTextIncludeSettings = {
|
|
101
|
+
requestBody?: boolean;
|
|
102
|
+
responseBody?: boolean;
|
|
103
|
+
};
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* Callback that is set using the `experimental_onStart` option.
|
|
107
|
+
*
|
|
108
|
+
* Called when the generateText operation begins, before any LLM calls.
|
|
109
|
+
* Use this callback for logging, analytics, or initializing state at the
|
|
110
|
+
* start of a generation.
|
|
111
|
+
*
|
|
112
|
+
* @param event - The event object containing generation configuration.
|
|
113
|
+
*/
|
|
114
|
+
export type GenerateTextOnStartCallback<
|
|
115
|
+
TOOLS extends ToolSet = ToolSet,
|
|
116
|
+
OUTPUT extends Output = Output,
|
|
117
|
+
> = (
|
|
118
|
+
event: OnStartEvent<TOOLS, OUTPUT, GenerateTextIncludeSettings>,
|
|
119
|
+
) => PromiseLike<void> | void;
|
|
120
|
+
|
|
121
|
+
/**
|
|
122
|
+
* Callback that is set using the `experimental_onStepStart` option.
|
|
123
|
+
*
|
|
124
|
+
* Called when a step (LLM call) begins, before the provider is called.
|
|
125
|
+
* Each step represents a single LLM invocation. Multiple steps occur when
|
|
126
|
+
* using tool calls (the model may be called multiple times in a loop).
|
|
127
|
+
*
|
|
128
|
+
* @param event - The event object containing step configuration.
|
|
129
|
+
*/
|
|
130
|
+
export type GenerateTextOnStepStartCallback<
|
|
131
|
+
TOOLS extends ToolSet = ToolSet,
|
|
132
|
+
OUTPUT extends Output = Output,
|
|
133
|
+
> = (
|
|
134
|
+
event: OnStepStartEvent<TOOLS, OUTPUT, GenerateTextIncludeSettings>,
|
|
135
|
+
) => PromiseLike<void> | void;
|
|
136
|
+
|
|
137
|
+
/**
|
|
138
|
+
* Callback that is set using the `experimental_onToolCallStart` option.
|
|
139
|
+
*
|
|
140
|
+
* Called when a tool execution begins, before the tool's `execute` function is invoked.
|
|
141
|
+
* Use this for logging tool invocations, tracking tool usage, or pre-execution validation.
|
|
142
|
+
*
|
|
143
|
+
* @param event - The event object containing tool call information.
|
|
144
|
+
*/
|
|
145
|
+
export type GenerateTextOnToolCallStartCallback<
|
|
146
|
+
TOOLS extends ToolSet = ToolSet,
|
|
147
|
+
> = (event: OnToolCallStartEvent<TOOLS>) => PromiseLike<void> | void;
|
|
148
|
+
|
|
149
|
+
/**
|
|
150
|
+
* Callback that is set using the `experimental_onToolCallFinish` option.
|
|
151
|
+
*
|
|
152
|
+
* Called when a tool execution completes, either successfully or with an error.
|
|
153
|
+
* Use this for logging tool results, tracking execution time, or error handling.
|
|
154
|
+
*
|
|
155
|
+
* The event uses a discriminated union on the `success` field:
|
|
156
|
+
* - When `success: true`: `output` contains the tool result, `error` is never present.
|
|
157
|
+
* - When `success: false`: `error` contains the error, `output` is never present.
|
|
158
|
+
*
|
|
159
|
+
* @param event - The event object containing tool call result information.
|
|
160
|
+
*/
|
|
161
|
+
export type GenerateTextOnToolCallFinishCallback<
|
|
162
|
+
TOOLS extends ToolSet = ToolSet,
|
|
163
|
+
> = (event: OnToolCallFinishEvent<TOOLS>) => PromiseLike<void> | void;
|
|
164
|
+
|
|
165
|
+
/**
|
|
166
|
+
* Callback that is set using the `onStepFinish` option.
|
|
167
|
+
*
|
|
168
|
+
* Called when a step (LLM call) completes. The event includes all step result
|
|
169
|
+
* properties (text, tool calls, usage, etc.) along with additional metadata.
|
|
170
|
+
*
|
|
171
|
+
* @param stepResult - The result of the step.
|
|
172
|
+
*/
|
|
173
|
+
export type GenerateTextOnStepFinishCallback<TOOLS extends ToolSet> = (
|
|
174
|
+
event: OnStepFinishEvent<TOOLS>,
|
|
175
|
+
) => Promise<void> | void;
|
|
176
|
+
|
|
177
|
+
/**
|
|
178
|
+
* Callback that is set using the `onFinish` option.
|
|
179
|
+
*
|
|
180
|
+
* Called when the entire generation completes (all steps finished).
|
|
181
|
+
* The event includes the final step's result properties along with
|
|
182
|
+
* aggregated data from all steps.
|
|
183
|
+
*
|
|
184
|
+
* @param event - The final result along with aggregated step data.
|
|
185
|
+
*/
|
|
186
|
+
export type GenerateTextOnFinishCallback<TOOLS extends ToolSet> = (
|
|
187
|
+
event: OnFinishEvent<TOOLS>,
|
|
188
|
+
) => PromiseLike<void> | void;
|
|
189
|
+
|
|
190
|
+
/**
|
|
191
|
+
* Generate a text and call tools for a given prompt using a language model.
|
|
192
|
+
*
|
|
193
|
+
* This function does not stream the output. If you want to stream the output, use `streamText` instead.
|
|
194
|
+
*
|
|
195
|
+
* @param model - The language model to use.
|
|
196
|
+
*
|
|
197
|
+
* @param tools - Tools that are accessible to and can be called by the model. The model needs to support calling tools.
|
|
198
|
+
* @param toolChoice - The tool choice strategy. Default: 'auto'.
|
|
199
|
+
*
|
|
200
|
+
* @param system - A system message that will be part of the prompt.
|
|
201
|
+
* @param prompt - A simple text prompt. You can either use `prompt` or `messages` but not both.
|
|
202
|
+
* @param messages - A list of messages. You can either use `prompt` or `messages` but not both.
|
|
203
|
+
*
|
|
204
|
+
* @param maxOutputTokens - Maximum number of tokens to generate.
|
|
205
|
+
* @param temperature - Temperature setting.
|
|
206
|
+
* The value is passed through to the provider. The range depends on the provider and model.
|
|
207
|
+
* It is recommended to set either `temperature` or `topP`, but not both.
|
|
208
|
+
* @param topP - Nucleus sampling.
|
|
209
|
+
* The value is passed through to the provider. The range depends on the provider and model.
|
|
210
|
+
* It is recommended to set either `temperature` or `topP`, but not both.
|
|
211
|
+
* @param topK - Only sample from the top K options for each subsequent token.
|
|
212
|
+
* Used to remove "long tail" low probability responses.
|
|
213
|
+
* Recommended for advanced use cases only. You usually only need to use temperature.
|
|
214
|
+
* @param presencePenalty - Presence penalty setting.
|
|
215
|
+
* It affects the likelihood of the model to repeat information that is already in the prompt.
|
|
216
|
+
* The value is passed through to the provider. The range depends on the provider and model.
|
|
217
|
+
* @param frequencyPenalty - Frequency penalty setting.
|
|
218
|
+
* It affects the likelihood of the model to repeatedly use the same words or phrases.
|
|
219
|
+
* The value is passed through to the provider. The range depends on the provider and model.
|
|
220
|
+
* @param stopSequences - Stop sequences.
|
|
221
|
+
* If set, the model will stop generating text when one of the stop sequences is generated.
|
|
222
|
+
* @param seed - The seed (integer) to use for random sampling.
|
|
223
|
+
* If set and supported by the model, calls will generate deterministic results.
|
|
224
|
+
*
|
|
225
|
+
* @param maxRetries - Maximum number of retries. Set to 0 to disable retries. Default: 2.
|
|
226
|
+
* @param abortSignal - An optional abort signal that can be used to cancel the call.
|
|
227
|
+
* @param timeout - An optional timeout in milliseconds. The call will be aborted if it takes longer than the specified timeout.
|
|
228
|
+
* @param headers - Additional HTTP headers to be sent with the request. Only applicable for HTTP-based providers.
|
|
229
|
+
*
|
|
230
|
+
* @param experimental_context - User-defined context object that flows through the entire generation lifecycle.
|
|
231
|
+
* @param experimental_onStart - Callback invoked when generation begins, before any LLM calls.
|
|
232
|
+
* @param experimental_onStepStart - Callback invoked when each step begins, before the provider is called.
|
|
233
|
+
* Receives step number, messages (in ModelMessage format), tools, and context.
|
|
234
|
+
* @param experimental_onToolCallStart - Callback invoked before each tool execution begins.
|
|
235
|
+
* Receives tool name, call ID, input, and context.
|
|
236
|
+
* @param experimental_onToolCallFinish - Callback invoked after each tool execution completes.
|
|
237
|
+
* Uses a discriminated union: check `success` to determine if `output` or `error` is present.
|
|
238
|
+
* @param onStepFinish - Callback that is called when each step (LLM call) is finished, including intermediate steps.
|
|
239
|
+
* @param onFinish - Callback that is called when all steps are finished and the response is complete.
|
|
240
|
+
*
|
|
241
|
+
* @returns
|
|
242
|
+
* A result object that contains the generated text, the results of the tool calls, and additional information.
|
|
243
|
+
*/
|
|
244
|
+
export async function generateText<
|
|
245
|
+
TOOLS extends ToolSet,
|
|
246
|
+
OUTPUT extends Output = Output<string, string>,
|
|
247
|
+
>({
|
|
248
|
+
model: modelArg,
|
|
249
|
+
tools,
|
|
250
|
+
toolChoice,
|
|
251
|
+
system,
|
|
252
|
+
prompt,
|
|
253
|
+
messages,
|
|
254
|
+
maxRetries: maxRetriesArg,
|
|
255
|
+
abortSignal,
|
|
256
|
+
timeout,
|
|
257
|
+
headers,
|
|
258
|
+
stopWhen = stepCountIs(1),
|
|
259
|
+
experimental_output,
|
|
260
|
+
output = experimental_output,
|
|
261
|
+
experimental_telemetry: telemetry,
|
|
262
|
+
providerOptions,
|
|
263
|
+
experimental_activeTools,
|
|
264
|
+
activeTools = experimental_activeTools,
|
|
265
|
+
experimental_prepareStep,
|
|
266
|
+
prepareStep = experimental_prepareStep,
|
|
267
|
+
experimental_repairToolCall: repairToolCall,
|
|
268
|
+
experimental_download: download,
|
|
269
|
+
experimental_context,
|
|
270
|
+
experimental_include: include,
|
|
271
|
+
experimental_fireAndForgetToolNames,
|
|
272
|
+
_internal: {
|
|
273
|
+
generateId = originalGenerateId,
|
|
274
|
+
generateCallId = originalGenerateCallId,
|
|
275
|
+
} = {},
|
|
276
|
+
experimental_onStart: onStart,
|
|
277
|
+
experimental_onStepStart: onStepStart,
|
|
278
|
+
experimental_onToolCallStart: onToolCallStart,
|
|
279
|
+
experimental_onToolCallFinish: onToolCallFinish,
|
|
280
|
+
onStepFinish,
|
|
281
|
+
onFinish,
|
|
282
|
+
...settings
|
|
283
|
+
}: CallSettings &
|
|
284
|
+
Prompt & {
|
|
285
|
+
/**
|
|
286
|
+
* The language model to use.
|
|
287
|
+
*/
|
|
288
|
+
model: LanguageModel;
|
|
289
|
+
|
|
290
|
+
/**
|
|
291
|
+
* Timeout in milliseconds. The call will be aborted if it takes longer
|
|
292
|
+
* than the specified timeout. Can be used alongside abortSignal.
|
|
293
|
+
*
|
|
294
|
+
* Can be specified as a number (milliseconds) or as an object with `totalMs`.
|
|
295
|
+
*/
|
|
296
|
+
timeout?: TimeoutConfiguration<TOOLS>;
|
|
297
|
+
|
|
298
|
+
/**
|
|
299
|
+
* The tools that the model can call. The model needs to support calling tools.
|
|
300
|
+
*/
|
|
301
|
+
tools?: TOOLS;
|
|
302
|
+
|
|
303
|
+
/**
|
|
304
|
+
* The tool choice strategy. Default: 'auto'.
|
|
305
|
+
*/
|
|
306
|
+
toolChoice?: ToolChoice<NoInfer<TOOLS>>;
|
|
307
|
+
|
|
308
|
+
/**
|
|
309
|
+
* Condition for stopping the generation when there are tool results in the last step.
|
|
310
|
+
* When the condition is an array, any of the conditions can be met to stop the generation.
|
|
311
|
+
*
|
|
312
|
+
* @default stepCountIs(1)
|
|
313
|
+
*/
|
|
314
|
+
stopWhen?:
|
|
315
|
+
| StopCondition<NoInfer<TOOLS>>
|
|
316
|
+
| Array<StopCondition<NoInfer<TOOLS>>>;
|
|
317
|
+
|
|
318
|
+
/**
|
|
319
|
+
* Optional telemetry configuration (experimental).
|
|
320
|
+
*/
|
|
321
|
+
experimental_telemetry?: TelemetrySettings;
|
|
322
|
+
|
|
323
|
+
/**
|
|
324
|
+
* Additional provider-specific options. They are passed through
|
|
325
|
+
* to the provider from the AI SDK and enable provider-specific
|
|
326
|
+
* functionality that can be fully encapsulated in the provider.
|
|
327
|
+
*/
|
|
328
|
+
providerOptions?: ProviderOptions;
|
|
329
|
+
|
|
330
|
+
/**
|
|
331
|
+
* @deprecated Use `activeTools` instead.
|
|
332
|
+
*/
|
|
333
|
+
experimental_activeTools?: Array<keyof NoInfer<TOOLS>>;
|
|
334
|
+
|
|
335
|
+
/**
|
|
336
|
+
* Limits the tools that are available for the model to call without
|
|
337
|
+
* changing the tool call and result types in the result.
|
|
338
|
+
*/
|
|
339
|
+
activeTools?: Array<keyof NoInfer<TOOLS>>;
|
|
340
|
+
|
|
341
|
+
/**
|
|
342
|
+
* Optional specification for parsing structured outputs from the LLM response.
|
|
343
|
+
*/
|
|
344
|
+
output?: OUTPUT;
|
|
345
|
+
|
|
346
|
+
/**
|
|
347
|
+
* Optional specification for parsing structured outputs from the LLM response.
|
|
348
|
+
*
|
|
349
|
+
* @deprecated Use `output` instead.
|
|
350
|
+
*/
|
|
351
|
+
experimental_output?: OUTPUT;
|
|
352
|
+
|
|
353
|
+
/**
|
|
354
|
+
* Custom download function to use for URLs.
|
|
355
|
+
*
|
|
356
|
+
* By default, files are downloaded if the model does not support the URL for the given media type.
|
|
357
|
+
*/
|
|
358
|
+
experimental_download?: DownloadFunction | undefined;
|
|
359
|
+
|
|
360
|
+
/**
|
|
361
|
+
* @deprecated Use `prepareStep` instead.
|
|
362
|
+
*/
|
|
363
|
+
experimental_prepareStep?: PrepareStepFunction<NoInfer<TOOLS>>;
|
|
364
|
+
|
|
365
|
+
/**
|
|
366
|
+
* Optional function that you can use to provide different settings for a step.
|
|
367
|
+
*/
|
|
368
|
+
prepareStep?: PrepareStepFunction<NoInfer<TOOLS>>;
|
|
369
|
+
|
|
370
|
+
/**
|
|
371
|
+
* A function that attempts to repair a tool call that failed to parse.
|
|
372
|
+
*/
|
|
373
|
+
experimental_repairToolCall?: ToolCallRepairFunction<NoInfer<TOOLS>>;
|
|
374
|
+
|
|
375
|
+
/**
|
|
376
|
+
* Callback that is called when the generateText operation begins,
|
|
377
|
+
* before any LLM calls are made.
|
|
378
|
+
*/
|
|
379
|
+
experimental_onStart?: GenerateTextOnStartCallback<NoInfer<TOOLS>, OUTPUT>;
|
|
380
|
+
|
|
381
|
+
/**
|
|
382
|
+
* Callback that is called when a step (LLM call) begins,
|
|
383
|
+
* before the provider is called.
|
|
384
|
+
*/
|
|
385
|
+
experimental_onStepStart?: GenerateTextOnStepStartCallback<
|
|
386
|
+
NoInfer<TOOLS>,
|
|
387
|
+
OUTPUT
|
|
388
|
+
>;
|
|
389
|
+
|
|
390
|
+
/**
|
|
391
|
+
* Callback that is called right before a tool's execute function runs.
|
|
392
|
+
*/
|
|
393
|
+
experimental_onToolCallStart?: GenerateTextOnToolCallStartCallback<
|
|
394
|
+
NoInfer<TOOLS>
|
|
395
|
+
>;
|
|
396
|
+
|
|
397
|
+
/**
|
|
398
|
+
* Callback that is called right after a tool's execute function completes (or errors).
|
|
399
|
+
*/
|
|
400
|
+
experimental_onToolCallFinish?: GenerateTextOnToolCallFinishCallback<
|
|
401
|
+
NoInfer<TOOLS>
|
|
402
|
+
>;
|
|
403
|
+
|
|
404
|
+
/**
|
|
405
|
+
* Callback that is called when each step (LLM call) is finished, including intermediate steps.
|
|
406
|
+
*/
|
|
407
|
+
onStepFinish?: GenerateTextOnStepFinishCallback<NoInfer<TOOLS>>;
|
|
408
|
+
|
|
409
|
+
/**
|
|
410
|
+
* Callback that is called when all steps are finished and the response is complete.
|
|
411
|
+
*/
|
|
412
|
+
onFinish?: GenerateTextOnFinishCallback<NoInfer<TOOLS>>;
|
|
413
|
+
|
|
414
|
+
/**
|
|
415
|
+
* Context that is passed into tool execution.
|
|
416
|
+
*
|
|
417
|
+
* Experimental (can break in patch releases).
|
|
418
|
+
*
|
|
419
|
+
* @default undefined
|
|
420
|
+
*/
|
|
421
|
+
experimental_context?: unknown;
|
|
422
|
+
|
|
423
|
+
/**
|
|
424
|
+
* Tool names that are treated as fire-and-forget (action tools).
|
|
425
|
+
* These tools are still executed for their side effects, but:
|
|
426
|
+
* - Their calls do not trigger a follow-up generation step
|
|
427
|
+
* - Their tool-call and tool-result are stripped from messages
|
|
428
|
+
* sent to the model in subsequent steps
|
|
429
|
+
*
|
|
430
|
+
* Use this for tools that perform side effects (e.g. setting a title,
|
|
431
|
+
* logging, notifications) whose results do not need to be incorporated
|
|
432
|
+
* into the model's response.
|
|
433
|
+
*/
|
|
434
|
+
experimental_fireAndForgetToolNames?: Array<keyof NoInfer<TOOLS>>;
|
|
435
|
+
|
|
436
|
+
/**
|
|
437
|
+
* Settings for controlling what data is included in step results.
|
|
438
|
+
* Disabling inclusion can help reduce memory usage when processing
|
|
439
|
+
* large payloads like images.
|
|
440
|
+
*
|
|
441
|
+
* By default, all data is included for backwards compatibility.
|
|
442
|
+
*/
|
|
443
|
+
experimental_include?: {
|
|
444
|
+
/**
|
|
445
|
+
* Whether to retain the request body in step results.
|
|
446
|
+
* The request body can be large when sending images or files.
|
|
447
|
+
* @default true
|
|
448
|
+
*/
|
|
449
|
+
requestBody?: boolean;
|
|
450
|
+
|
|
451
|
+
/**
|
|
452
|
+
* Whether to retain the response body in step results.
|
|
453
|
+
* @default true
|
|
454
|
+
*/
|
|
455
|
+
responseBody?: boolean;
|
|
456
|
+
};
|
|
457
|
+
|
|
458
|
+
/**
|
|
459
|
+
* Internal. For test use only. May change without notice.
|
|
460
|
+
*/
|
|
461
|
+
_internal?: {
|
|
462
|
+
generateId?: IdGenerator;
|
|
463
|
+
generateCallId?: IdGenerator;
|
|
464
|
+
};
|
|
465
|
+
}): Promise<GenerateTextResult<TOOLS, OUTPUT>> {
|
|
466
|
+
const model = resolveLanguageModel(modelArg);
|
|
467
|
+
const createGlobalTelemetry = getGlobalTelemetryIntegration<TOOLS, OUTPUT>();
|
|
468
|
+
const stopConditions = asArray(stopWhen);
|
|
469
|
+
|
|
470
|
+
const totalTimeoutMs = getTotalTimeoutMs(timeout);
|
|
471
|
+
const stepTimeoutMs = getStepTimeoutMs(timeout);
|
|
472
|
+
const stepAbortController =
|
|
473
|
+
stepTimeoutMs != null ? new AbortController() : undefined;
|
|
474
|
+
const mergedAbortSignal = mergeAbortSignals(
|
|
475
|
+
abortSignal,
|
|
476
|
+
totalTimeoutMs != null ? AbortSignal.timeout(totalTimeoutMs) : undefined,
|
|
477
|
+
stepAbortController?.signal,
|
|
478
|
+
);
|
|
479
|
+
|
|
480
|
+
const { maxRetries, retry } = prepareRetries({
|
|
481
|
+
maxRetries: maxRetriesArg,
|
|
482
|
+
abortSignal: mergedAbortSignal,
|
|
483
|
+
});
|
|
484
|
+
|
|
485
|
+
const callSettings = prepareCallSettings(settings);
|
|
486
|
+
|
|
487
|
+
const headersWithUserAgent = withUserAgentSuffix(
|
|
488
|
+
headers ?? {},
|
|
489
|
+
`ai/${VERSION}`,
|
|
490
|
+
);
|
|
491
|
+
|
|
492
|
+
const initialPrompt = await standardizePrompt({
|
|
493
|
+
system,
|
|
494
|
+
prompt,
|
|
495
|
+
messages,
|
|
496
|
+
} as Prompt);
|
|
497
|
+
|
|
498
|
+
const callId = generateCallId();
|
|
499
|
+
const globalTelemetry = createGlobalTelemetry({
|
|
500
|
+
integrations: telemetry?.integrations,
|
|
501
|
+
});
|
|
502
|
+
|
|
503
|
+
await notify({
|
|
504
|
+
event: {
|
|
505
|
+
callId,
|
|
506
|
+
operationId: 'ai.generateText',
|
|
507
|
+
provider: model.provider,
|
|
508
|
+
modelId: model.modelId,
|
|
509
|
+
system,
|
|
510
|
+
prompt,
|
|
511
|
+
messages,
|
|
512
|
+
tools,
|
|
513
|
+
toolChoice,
|
|
514
|
+
activeTools,
|
|
515
|
+
maxOutputTokens: callSettings.maxOutputTokens,
|
|
516
|
+
temperature: callSettings.temperature,
|
|
517
|
+
topP: callSettings.topP,
|
|
518
|
+
topK: callSettings.topK,
|
|
519
|
+
presencePenalty: callSettings.presencePenalty,
|
|
520
|
+
frequencyPenalty: callSettings.frequencyPenalty,
|
|
521
|
+
stopSequences: callSettings.stopSequences,
|
|
522
|
+
seed: callSettings.seed,
|
|
523
|
+
reasoning: callSettings.reasoning,
|
|
524
|
+
maxRetries,
|
|
525
|
+
timeout,
|
|
526
|
+
headers: headersWithUserAgent,
|
|
527
|
+
providerOptions,
|
|
528
|
+
stopWhen,
|
|
529
|
+
output,
|
|
530
|
+
abortSignal,
|
|
531
|
+
include,
|
|
532
|
+
isEnabled: telemetry?.isEnabled,
|
|
533
|
+
recordInputs: telemetry?.recordInputs,
|
|
534
|
+
recordOutputs: telemetry?.recordOutputs,
|
|
535
|
+
functionId: telemetry?.functionId,
|
|
536
|
+
metadata: telemetry?.metadata,
|
|
537
|
+
experimental_context,
|
|
538
|
+
},
|
|
539
|
+
callbacks: [
|
|
540
|
+
onStart,
|
|
541
|
+
globalTelemetry.onStart as
|
|
542
|
+
| undefined
|
|
543
|
+
| GenerateTextOnStartCallback<TOOLS, OUTPUT>,
|
|
544
|
+
],
|
|
545
|
+
});
|
|
546
|
+
|
|
547
|
+
try {
|
|
548
|
+
const initialMessages = initialPrompt.messages;
|
|
549
|
+
const responseMessages: Array<ResponseMessage> = [];
|
|
550
|
+
|
|
551
|
+
const { approvedToolApprovals, deniedToolApprovals } =
|
|
552
|
+
collectToolApprovals<TOOLS>({ messages: initialMessages });
|
|
553
|
+
|
|
554
|
+
const localApprovedToolApprovals = approvedToolApprovals.filter(
|
|
555
|
+
toolApproval => !toolApproval.toolCall.providerExecuted,
|
|
556
|
+
);
|
|
557
|
+
|
|
558
|
+
if (
|
|
559
|
+
deniedToolApprovals.length > 0 ||
|
|
560
|
+
localApprovedToolApprovals.length > 0
|
|
561
|
+
) {
|
|
562
|
+
const toolOutputs = await executeTools({
|
|
563
|
+
toolCalls: localApprovedToolApprovals.map(
|
|
564
|
+
toolApproval => toolApproval.toolCall,
|
|
565
|
+
),
|
|
566
|
+
tools: tools as TOOLS,
|
|
567
|
+
telemetry,
|
|
568
|
+
callId,
|
|
569
|
+
messages: initialMessages,
|
|
570
|
+
abortSignal: mergedAbortSignal,
|
|
571
|
+
timeout,
|
|
572
|
+
experimental_context,
|
|
573
|
+
stepNumber: 0,
|
|
574
|
+
provider: model.provider,
|
|
575
|
+
modelId: model.modelId,
|
|
576
|
+
onToolCallStart: event =>
|
|
577
|
+
notify({
|
|
578
|
+
event,
|
|
579
|
+
callbacks: [
|
|
580
|
+
onToolCallStart,
|
|
581
|
+
globalTelemetry.onToolCallStart as
|
|
582
|
+
| undefined
|
|
583
|
+
| GenerateTextOnToolCallStartCallback<TOOLS>,
|
|
584
|
+
],
|
|
585
|
+
}),
|
|
586
|
+
onToolCallFinish: event =>
|
|
587
|
+
notify({
|
|
588
|
+
event,
|
|
589
|
+
callbacks: [
|
|
590
|
+
onToolCallFinish,
|
|
591
|
+
globalTelemetry.onToolCallFinish as
|
|
592
|
+
| undefined
|
|
593
|
+
| GenerateTextOnToolCallFinishCallback<TOOLS>,
|
|
594
|
+
],
|
|
595
|
+
}),
|
|
596
|
+
executeToolInTelemetryContext: globalTelemetry.executeTool,
|
|
597
|
+
});
|
|
598
|
+
|
|
599
|
+
const toolContent: Array<any> = [];
|
|
600
|
+
|
|
601
|
+
// add regular tool results for approved tool calls:
|
|
602
|
+
for (const output of toolOutputs) {
|
|
603
|
+
const modelOutput = await createToolModelOutput({
|
|
604
|
+
toolCallId: output.toolCallId,
|
|
605
|
+
input: output.input,
|
|
606
|
+
tool: tools?.[output.toolName],
|
|
607
|
+
output: output.type === 'tool-result' ? output.output : output.error,
|
|
608
|
+
errorMode: output.type === 'tool-error' ? 'text' : 'none',
|
|
609
|
+
});
|
|
610
|
+
|
|
611
|
+
toolContent.push({
|
|
612
|
+
type: 'tool-result' as const,
|
|
613
|
+
toolCallId: output.toolCallId,
|
|
614
|
+
toolName: output.toolName,
|
|
615
|
+
output: modelOutput,
|
|
616
|
+
});
|
|
617
|
+
}
|
|
618
|
+
|
|
619
|
+
// add execution denied tool results for all denied tool approvals:
|
|
620
|
+
for (const toolApproval of deniedToolApprovals) {
|
|
621
|
+
toolContent.push({
|
|
622
|
+
type: 'tool-result' as const,
|
|
623
|
+
toolCallId: toolApproval.toolCall.toolCallId,
|
|
624
|
+
toolName: toolApproval.toolCall.toolName,
|
|
625
|
+
output: {
|
|
626
|
+
type: 'execution-denied' as const,
|
|
627
|
+
reason: toolApproval.approvalResponse.reason,
|
|
628
|
+
// For provider-executed tools, include approvalId so provider can correlate
|
|
629
|
+
...(toolApproval.toolCall.providerExecuted && {
|
|
630
|
+
providerOptions: {
|
|
631
|
+
openai: {
|
|
632
|
+
approvalId: toolApproval.approvalResponse.approvalId,
|
|
633
|
+
},
|
|
634
|
+
},
|
|
635
|
+
}),
|
|
636
|
+
},
|
|
637
|
+
});
|
|
638
|
+
}
|
|
639
|
+
|
|
640
|
+
responseMessages.push({
|
|
641
|
+
role: 'tool',
|
|
642
|
+
content: toolContent,
|
|
643
|
+
});
|
|
644
|
+
}
|
|
645
|
+
|
|
646
|
+
// Forward provider-executed approval responses to the provider
|
|
647
|
+
const providerExecutedToolApprovals = [
|
|
648
|
+
...approvedToolApprovals,
|
|
649
|
+
...deniedToolApprovals,
|
|
650
|
+
].filter(toolApproval => toolApproval.toolCall.providerExecuted);
|
|
651
|
+
|
|
652
|
+
if (providerExecutedToolApprovals.length > 0) {
|
|
653
|
+
responseMessages.push({
|
|
654
|
+
role: 'tool',
|
|
655
|
+
content: providerExecutedToolApprovals.map(
|
|
656
|
+
toolApproval =>
|
|
657
|
+
({
|
|
658
|
+
type: 'tool-approval-response',
|
|
659
|
+
approvalId: toolApproval.approvalResponse.approvalId,
|
|
660
|
+
approved: toolApproval.approvalResponse.approved,
|
|
661
|
+
reason: toolApproval.approvalResponse.reason,
|
|
662
|
+
providerExecuted: true,
|
|
663
|
+
}) satisfies ToolApprovalResponse,
|
|
664
|
+
),
|
|
665
|
+
});
|
|
666
|
+
}
|
|
667
|
+
|
|
668
|
+
const callSettings = prepareCallSettings(settings);
|
|
669
|
+
|
|
670
|
+
let currentModelResponse: Awaited<
|
|
671
|
+
ReturnType<LanguageModelV4['doGenerate']>
|
|
672
|
+
> & { response: { id: string; timestamp: Date; modelId: string } };
|
|
673
|
+
const fireAndForgetTools = new Set(
|
|
674
|
+
experimental_fireAndForgetToolNames?.map(String) ?? [],
|
|
675
|
+
);
|
|
676
|
+
let clientToolCalls: Array<TypedToolCall<TOOLS>> = [];
|
|
677
|
+
let continuableToolCalls: Array<TypedToolCall<TOOLS>> = [];
|
|
678
|
+
let clientToolOutputs: Array<ToolOutput<TOOLS>> = [];
|
|
679
|
+
const steps: GenerateTextResult<TOOLS, OUTPUT>['steps'] = [];
|
|
680
|
+
|
|
681
|
+
// Track provider-executed tool calls that support deferred results
|
|
682
|
+
// (e.g., code_execution in programmatic tool calling scenarios).
|
|
683
|
+
// These tools may not return their results in the same turn as their call.
|
|
684
|
+
const pendingDeferredToolCalls = new Map<string, { toolName: string }>();
|
|
685
|
+
|
|
686
|
+
do {
|
|
687
|
+
// Set up step timeout if configured
|
|
688
|
+
const stepTimeoutId =
|
|
689
|
+
stepTimeoutMs != null
|
|
690
|
+
? setTimeout(() => stepAbortController!.abort(), stepTimeoutMs)
|
|
691
|
+
: undefined;
|
|
692
|
+
|
|
693
|
+
try {
|
|
694
|
+
const stepInputMessages = [...initialMessages, ...responseMessages];
|
|
695
|
+
|
|
696
|
+
const prepareStepResult = await prepareStep?.({
|
|
697
|
+
model,
|
|
698
|
+
steps,
|
|
699
|
+
stepNumber: steps.length,
|
|
700
|
+
messages: stepInputMessages,
|
|
701
|
+
experimental_context,
|
|
702
|
+
});
|
|
703
|
+
|
|
704
|
+
const stepModel = resolveLanguageModel(
|
|
705
|
+
prepareStepResult?.model ?? model,
|
|
706
|
+
);
|
|
707
|
+
|
|
708
|
+
const promptMessages = await convertToLanguageModelPrompt({
|
|
709
|
+
prompt: {
|
|
710
|
+
system: prepareStepResult?.system ?? initialPrompt.system,
|
|
711
|
+
messages: prepareStepResult?.messages ?? stepInputMessages,
|
|
712
|
+
},
|
|
713
|
+
supportedUrls: await stepModel.supportedUrls,
|
|
714
|
+
download,
|
|
715
|
+
});
|
|
716
|
+
|
|
717
|
+
experimental_context =
|
|
718
|
+
prepareStepResult?.experimental_context ?? experimental_context;
|
|
719
|
+
|
|
720
|
+
const stepActiveTools = prepareStepResult?.activeTools ?? activeTools;
|
|
721
|
+
|
|
722
|
+
const { toolChoice: stepToolChoice, tools: stepTools } =
|
|
723
|
+
await prepareToolsAndToolChoice({
|
|
724
|
+
tools,
|
|
725
|
+
toolChoice: prepareStepResult?.toolChoice ?? toolChoice,
|
|
726
|
+
activeTools: stepActiveTools,
|
|
727
|
+
});
|
|
728
|
+
|
|
729
|
+
const stepMessages = prepareStepResult?.messages ?? stepInputMessages;
|
|
730
|
+
|
|
731
|
+
const stepSystem = prepareStepResult?.system ?? initialPrompt.system;
|
|
732
|
+
|
|
733
|
+
const stepProviderOptions = mergeObjects(
|
|
734
|
+
providerOptions,
|
|
735
|
+
prepareStepResult?.providerOptions,
|
|
736
|
+
);
|
|
737
|
+
|
|
738
|
+
const onStepStartEvent = {
|
|
739
|
+
callId,
|
|
740
|
+
stepNumber: steps.length,
|
|
741
|
+
provider: stepModel.provider,
|
|
742
|
+
modelId: stepModel.modelId,
|
|
743
|
+
system: stepSystem,
|
|
744
|
+
messages: stepMessages,
|
|
745
|
+
tools,
|
|
746
|
+
toolChoice: stepToolChoice,
|
|
747
|
+
activeTools: stepActiveTools,
|
|
748
|
+
steps: [...steps],
|
|
749
|
+
providerOptions: stepProviderOptions,
|
|
750
|
+
timeout,
|
|
751
|
+
headers,
|
|
752
|
+
stopWhen,
|
|
753
|
+
output,
|
|
754
|
+
abortSignal,
|
|
755
|
+
include,
|
|
756
|
+
functionId: telemetry?.functionId,
|
|
757
|
+
metadata: telemetry?.metadata as Record<string, unknown> | undefined,
|
|
758
|
+
experimental_context,
|
|
759
|
+
promptMessages,
|
|
760
|
+
stepTools,
|
|
761
|
+
stepToolChoice,
|
|
762
|
+
};
|
|
763
|
+
|
|
764
|
+
await notify({
|
|
765
|
+
event: onStepStartEvent,
|
|
766
|
+
callbacks: [
|
|
767
|
+
onStepStart,
|
|
768
|
+
globalTelemetry.onStepStart as
|
|
769
|
+
| undefined
|
|
770
|
+
| GenerateTextOnStepStartCallback<TOOLS, OUTPUT>,
|
|
771
|
+
],
|
|
772
|
+
});
|
|
773
|
+
|
|
774
|
+
currentModelResponse = await retry(async () => {
|
|
775
|
+
const result = await stepModel.doGenerate({
|
|
776
|
+
...callSettings,
|
|
777
|
+
tools: stepTools,
|
|
778
|
+
toolChoice: stepToolChoice,
|
|
779
|
+
responseFormat: await output?.responseFormat,
|
|
780
|
+
prompt: promptMessages,
|
|
781
|
+
providerOptions: stepProviderOptions,
|
|
782
|
+
abortSignal: mergedAbortSignal,
|
|
783
|
+
headers: headersWithUserAgent,
|
|
784
|
+
});
|
|
785
|
+
|
|
786
|
+
const responseData = {
|
|
787
|
+
id: result.response?.id ?? generateId(),
|
|
788
|
+
timestamp: result.response?.timestamp ?? new Date(),
|
|
789
|
+
modelId: result.response?.modelId ?? stepModel.modelId,
|
|
790
|
+
headers: result.response?.headers,
|
|
791
|
+
body: result.response?.body,
|
|
792
|
+
};
|
|
793
|
+
|
|
794
|
+
return { ...result, response: responseData };
|
|
795
|
+
});
|
|
796
|
+
|
|
797
|
+
// parse tool calls:
|
|
798
|
+
const stepToolCalls: TypedToolCall<TOOLS>[] = await Promise.all(
|
|
799
|
+
currentModelResponse.content
|
|
800
|
+
.filter(
|
|
801
|
+
(part): part is LanguageModelV4ToolCall =>
|
|
802
|
+
part.type === 'tool-call',
|
|
803
|
+
)
|
|
804
|
+
.map(toolCall =>
|
|
805
|
+
parseToolCall({
|
|
806
|
+
toolCall,
|
|
807
|
+
tools,
|
|
808
|
+
repairToolCall,
|
|
809
|
+
system,
|
|
810
|
+
messages: stepInputMessages,
|
|
811
|
+
}),
|
|
812
|
+
),
|
|
813
|
+
);
|
|
814
|
+
const toolApprovalRequests: Record<
|
|
815
|
+
string,
|
|
816
|
+
ToolApprovalRequestOutput<TOOLS>
|
|
817
|
+
> = {};
|
|
818
|
+
|
|
819
|
+
// notify the tools that the tool calls are available:
|
|
820
|
+
for (const toolCall of stepToolCalls) {
|
|
821
|
+
if (toolCall.invalid) {
|
|
822
|
+
continue; // ignore invalid tool calls
|
|
823
|
+
}
|
|
824
|
+
|
|
825
|
+
const tool = tools?.[toolCall.toolName];
|
|
826
|
+
|
|
827
|
+
if (tool == null) {
|
|
828
|
+
// ignore tool calls for tools that are not available,
|
|
829
|
+
// e.g. provider-executed dynamic tools
|
|
830
|
+
continue;
|
|
831
|
+
}
|
|
832
|
+
|
|
833
|
+
if (tool?.onInputAvailable != null) {
|
|
834
|
+
await tool.onInputAvailable({
|
|
835
|
+
input: toolCall.input,
|
|
836
|
+
toolCallId: toolCall.toolCallId,
|
|
837
|
+
messages: stepInputMessages,
|
|
838
|
+
abortSignal: mergedAbortSignal,
|
|
839
|
+
experimental_context,
|
|
840
|
+
});
|
|
841
|
+
}
|
|
842
|
+
|
|
843
|
+
if (
|
|
844
|
+
await isApprovalNeeded({
|
|
845
|
+
tool,
|
|
846
|
+
toolCall,
|
|
847
|
+
messages: stepInputMessages,
|
|
848
|
+
experimental_context,
|
|
849
|
+
})
|
|
850
|
+
) {
|
|
851
|
+
toolApprovalRequests[toolCall.toolCallId] = {
|
|
852
|
+
type: 'tool-approval-request',
|
|
853
|
+
approvalId: generateId(),
|
|
854
|
+
toolCall,
|
|
855
|
+
};
|
|
856
|
+
}
|
|
857
|
+
}
|
|
858
|
+
|
|
859
|
+
// insert error tool outputs for invalid tool calls:
|
|
860
|
+
// TODO AI SDK 6: invalid inputs should not require output parts
|
|
861
|
+
const invalidToolCalls = stepToolCalls.filter(
|
|
862
|
+
toolCall => toolCall.invalid && toolCall.dynamic,
|
|
863
|
+
);
|
|
864
|
+
|
|
865
|
+
clientToolOutputs = [];
|
|
866
|
+
|
|
867
|
+
for (const toolCall of invalidToolCalls) {
|
|
868
|
+
clientToolOutputs.push({
|
|
869
|
+
type: 'tool-error',
|
|
870
|
+
toolCallId: toolCall.toolCallId,
|
|
871
|
+
toolName: toolCall.toolName,
|
|
872
|
+
input: toolCall.input,
|
|
873
|
+
error: getErrorMessage(toolCall.error!),
|
|
874
|
+
dynamic: true,
|
|
875
|
+
});
|
|
876
|
+
}
|
|
877
|
+
|
|
878
|
+
// execute client tool calls (including fire-and-forget tools for side effects):
|
|
879
|
+
clientToolCalls = stepToolCalls.filter(
|
|
880
|
+
toolCall => !toolCall.providerExecuted,
|
|
881
|
+
);
|
|
882
|
+
|
|
883
|
+
// continuable tool calls exclude fire-and-forget tools from loop continuation:
|
|
884
|
+
continuableToolCalls = clientToolCalls.filter(
|
|
885
|
+
toolCall => !fireAndForgetTools.has(toolCall.toolName),
|
|
886
|
+
);
|
|
887
|
+
|
|
888
|
+
if (tools != null) {
|
|
889
|
+
clientToolOutputs.push(
|
|
890
|
+
...(await executeTools({
|
|
891
|
+
toolCalls: clientToolCalls.filter(
|
|
892
|
+
toolCall =>
|
|
893
|
+
!toolCall.invalid &&
|
|
894
|
+
toolApprovalRequests[toolCall.toolCallId] == null,
|
|
895
|
+
),
|
|
896
|
+
tools,
|
|
897
|
+
telemetry,
|
|
898
|
+
callId,
|
|
899
|
+
messages: stepInputMessages,
|
|
900
|
+
abortSignal: mergedAbortSignal,
|
|
901
|
+
timeout,
|
|
902
|
+
experimental_context,
|
|
903
|
+
stepNumber: steps.length,
|
|
904
|
+
provider: stepModel.provider,
|
|
905
|
+
modelId: stepModel.modelId,
|
|
906
|
+
onToolCallStart: event =>
|
|
907
|
+
notify({
|
|
908
|
+
event,
|
|
909
|
+
callbacks: [
|
|
910
|
+
onToolCallStart,
|
|
911
|
+
globalTelemetry.onToolCallStart as
|
|
912
|
+
| undefined
|
|
913
|
+
| GenerateTextOnToolCallStartCallback<TOOLS>,
|
|
914
|
+
],
|
|
915
|
+
}),
|
|
916
|
+
onToolCallFinish: event =>
|
|
917
|
+
notify({
|
|
918
|
+
event,
|
|
919
|
+
callbacks: [
|
|
920
|
+
onToolCallFinish,
|
|
921
|
+
globalTelemetry.onToolCallFinish as
|
|
922
|
+
| undefined
|
|
923
|
+
| GenerateTextOnToolCallFinishCallback<TOOLS>,
|
|
924
|
+
],
|
|
925
|
+
}),
|
|
926
|
+
executeToolInTelemetryContext: globalTelemetry.executeTool,
|
|
927
|
+
})),
|
|
928
|
+
);
|
|
929
|
+
}
|
|
930
|
+
|
|
931
|
+
// Track provider-executed tool calls that support deferred results.
|
|
932
|
+
// In programmatic tool calling, a server tool (e.g., code_execution) may
|
|
933
|
+
// trigger a client tool, and the server tool's result is deferred until
|
|
934
|
+
// the client tool's result is sent back.
|
|
935
|
+
for (const toolCall of stepToolCalls) {
|
|
936
|
+
if (!toolCall.providerExecuted) continue;
|
|
937
|
+
const tool = tools?.[toolCall.toolName];
|
|
938
|
+
if (tool?.type === 'provider' && tool.supportsDeferredResults) {
|
|
939
|
+
// Check if this tool call already has a result in the current response
|
|
940
|
+
const hasResultInResponse = currentModelResponse.content.some(
|
|
941
|
+
part =>
|
|
942
|
+
part.type === 'tool-result' &&
|
|
943
|
+
part.toolCallId === toolCall.toolCallId,
|
|
944
|
+
);
|
|
945
|
+
if (!hasResultInResponse) {
|
|
946
|
+
pendingDeferredToolCalls.set(toolCall.toolCallId, {
|
|
947
|
+
toolName: toolCall.toolName,
|
|
948
|
+
});
|
|
949
|
+
}
|
|
950
|
+
}
|
|
951
|
+
}
|
|
952
|
+
|
|
953
|
+
// Mark deferred tool calls as resolved when we receive their results
|
|
954
|
+
for (const part of currentModelResponse.content) {
|
|
955
|
+
if (part.type === 'tool-result') {
|
|
956
|
+
pendingDeferredToolCalls.delete(part.toolCallId);
|
|
957
|
+
}
|
|
958
|
+
}
|
|
959
|
+
|
|
960
|
+
// content:
|
|
961
|
+
const stepContent = asContent({
|
|
962
|
+
content: currentModelResponse.content,
|
|
963
|
+
toolCalls: stepToolCalls,
|
|
964
|
+
toolOutputs: clientToolOutputs,
|
|
965
|
+
toolApprovalRequests: Object.values(toolApprovalRequests),
|
|
966
|
+
tools,
|
|
967
|
+
});
|
|
968
|
+
|
|
969
|
+
// append to messages for potential next step:
|
|
970
|
+
responseMessages.push(
|
|
971
|
+
...(await toResponseMessages({
|
|
972
|
+
content: stepContent,
|
|
973
|
+
tools,
|
|
974
|
+
fireAndForgetTools,
|
|
975
|
+
})),
|
|
976
|
+
);
|
|
977
|
+
|
|
978
|
+
// Add step information (after response messages are updated):
|
|
979
|
+
// Conditionally include request.body and response.body based on include settings.
|
|
980
|
+
// Large payloads (e.g., base64-encoded images) can cause memory issues.
|
|
981
|
+
const stepRequest: LanguageModelRequestMetadata =
|
|
982
|
+
(include?.requestBody ?? true)
|
|
983
|
+
? (currentModelResponse.request ?? {})
|
|
984
|
+
: { ...currentModelResponse.request, body: undefined };
|
|
985
|
+
|
|
986
|
+
const stepResponse = {
|
|
987
|
+
...currentModelResponse.response,
|
|
988
|
+
// deep clone msgs to avoid mutating past messages in multi-step:
|
|
989
|
+
messages: structuredClone(responseMessages),
|
|
990
|
+
// Conditionally include response body:
|
|
991
|
+
body:
|
|
992
|
+
(include?.responseBody ?? true)
|
|
993
|
+
? currentModelResponse.response?.body
|
|
994
|
+
: undefined,
|
|
995
|
+
};
|
|
996
|
+
|
|
997
|
+
const stepNumber = steps.length;
|
|
998
|
+
|
|
999
|
+
const currentStepResult: StepResult<TOOLS> = new DefaultStepResult({
|
|
1000
|
+
callId,
|
|
1001
|
+
stepNumber,
|
|
1002
|
+
provider: stepModel.provider,
|
|
1003
|
+
modelId: stepModel.modelId,
|
|
1004
|
+
functionId: telemetry?.functionId,
|
|
1005
|
+
metadata: telemetry?.metadata as Record<string, unknown> | undefined,
|
|
1006
|
+
experimental_context,
|
|
1007
|
+
content: stepContent,
|
|
1008
|
+
finishReason: currentModelResponse.finishReason.unified,
|
|
1009
|
+
rawFinishReason: currentModelResponse.finishReason.raw,
|
|
1010
|
+
usage: asLanguageModelUsage(currentModelResponse.usage),
|
|
1011
|
+
warnings: currentModelResponse.warnings,
|
|
1012
|
+
providerMetadata: currentModelResponse.providerMetadata,
|
|
1013
|
+
request: stepRequest,
|
|
1014
|
+
response: stepResponse,
|
|
1015
|
+
});
|
|
1016
|
+
|
|
1017
|
+
logWarnings({
|
|
1018
|
+
warnings: currentModelResponse.warnings ?? [],
|
|
1019
|
+
provider: stepModel.provider,
|
|
1020
|
+
model: stepModel.modelId,
|
|
1021
|
+
});
|
|
1022
|
+
|
|
1023
|
+
steps.push(currentStepResult);
|
|
1024
|
+
|
|
1025
|
+
await notify({
|
|
1026
|
+
event: currentStepResult,
|
|
1027
|
+
callbacks: [
|
|
1028
|
+
onStepFinish,
|
|
1029
|
+
globalTelemetry.onStepFinish as
|
|
1030
|
+
| undefined
|
|
1031
|
+
| GenerateTextOnStepFinishCallback<TOOLS>,
|
|
1032
|
+
],
|
|
1033
|
+
});
|
|
1034
|
+
} finally {
|
|
1035
|
+
if (stepTimeoutId != null) {
|
|
1036
|
+
clearTimeout(stepTimeoutId);
|
|
1037
|
+
}
|
|
1038
|
+
}
|
|
1039
|
+
} while (
|
|
1040
|
+
// Continue if:
|
|
1041
|
+
// 1. There are continuable (non-fire-and-forget) client tool calls
|
|
1042
|
+
// that have all been executed, OR
|
|
1043
|
+
// 2. There are pending deferred results from provider-executed tools
|
|
1044
|
+
((continuableToolCalls.length > 0 &&
|
|
1045
|
+
clientToolOutputs.filter(o => !fireAndForgetTools.has(o.toolName))
|
|
1046
|
+
.length === continuableToolCalls.length) ||
|
|
1047
|
+
pendingDeferredToolCalls.size > 0) &&
|
|
1048
|
+
// continue until a stop condition is met:
|
|
1049
|
+
!(await isStopConditionMet({ stopConditions, steps }))
|
|
1050
|
+
);
|
|
1051
|
+
|
|
1052
|
+
const lastStep = steps[steps.length - 1];
|
|
1053
|
+
|
|
1054
|
+
const totalUsage = steps.reduce(
|
|
1055
|
+
(totalUsage, step) => {
|
|
1056
|
+
return addLanguageModelUsage(totalUsage, step.usage);
|
|
1057
|
+
},
|
|
1058
|
+
{
|
|
1059
|
+
inputTokens: undefined,
|
|
1060
|
+
outputTokens: undefined,
|
|
1061
|
+
totalTokens: undefined,
|
|
1062
|
+
reasoningTokens: undefined,
|
|
1063
|
+
cachedInputTokens: undefined,
|
|
1064
|
+
} as LanguageModelUsage,
|
|
1065
|
+
);
|
|
1066
|
+
|
|
1067
|
+
const onFinishEvent = {
|
|
1068
|
+
callId,
|
|
1069
|
+
stepNumber: lastStep.stepNumber,
|
|
1070
|
+
model: lastStep.model,
|
|
1071
|
+
functionId: lastStep.functionId,
|
|
1072
|
+
metadata: lastStep.metadata,
|
|
1073
|
+
experimental_context: lastStep.experimental_context,
|
|
1074
|
+
finishReason: lastStep.finishReason,
|
|
1075
|
+
rawFinishReason: lastStep.rawFinishReason,
|
|
1076
|
+
usage: lastStep.usage,
|
|
1077
|
+
content: lastStep.content,
|
|
1078
|
+
text: lastStep.text,
|
|
1079
|
+
reasoningText: lastStep.reasoningText,
|
|
1080
|
+
reasoning: lastStep.reasoning,
|
|
1081
|
+
files: lastStep.files,
|
|
1082
|
+
sources: lastStep.sources,
|
|
1083
|
+
toolCalls: lastStep.toolCalls,
|
|
1084
|
+
staticToolCalls: lastStep.staticToolCalls,
|
|
1085
|
+
dynamicToolCalls: lastStep.dynamicToolCalls,
|
|
1086
|
+
toolResults: lastStep.toolResults,
|
|
1087
|
+
staticToolResults: lastStep.staticToolResults,
|
|
1088
|
+
dynamicToolResults: lastStep.dynamicToolResults,
|
|
1089
|
+
request: lastStep.request,
|
|
1090
|
+
response: lastStep.response,
|
|
1091
|
+
warnings: lastStep.warnings,
|
|
1092
|
+
providerMetadata: lastStep.providerMetadata,
|
|
1093
|
+
steps,
|
|
1094
|
+
totalUsage,
|
|
1095
|
+
};
|
|
1096
|
+
|
|
1097
|
+
await notify({
|
|
1098
|
+
event: onFinishEvent,
|
|
1099
|
+
callbacks: [
|
|
1100
|
+
onFinish,
|
|
1101
|
+
globalTelemetry.onFinish as
|
|
1102
|
+
| undefined
|
|
1103
|
+
| GenerateTextOnFinishCallback<TOOLS>,
|
|
1104
|
+
],
|
|
1105
|
+
});
|
|
1106
|
+
|
|
1107
|
+
// parse output only if the last step was finished with "stop":
|
|
1108
|
+
let resolvedOutput;
|
|
1109
|
+
if (lastStep.finishReason === 'stop') {
|
|
1110
|
+
const outputSpecification = output ?? text();
|
|
1111
|
+
resolvedOutput = await outputSpecification.parseCompleteOutput(
|
|
1112
|
+
{ text: lastStep.text },
|
|
1113
|
+
{
|
|
1114
|
+
response: lastStep.response,
|
|
1115
|
+
usage: lastStep.usage,
|
|
1116
|
+
finishReason: lastStep.finishReason,
|
|
1117
|
+
},
|
|
1118
|
+
);
|
|
1119
|
+
}
|
|
1120
|
+
|
|
1121
|
+
return new DefaultGenerateTextResult({
|
|
1122
|
+
steps,
|
|
1123
|
+
totalUsage,
|
|
1124
|
+
output: resolvedOutput,
|
|
1125
|
+
});
|
|
1126
|
+
} catch (error) {
|
|
1127
|
+
await globalTelemetry.onError?.({ callId, error });
|
|
1128
|
+
throw wrapGatewayError(error);
|
|
1129
|
+
}
|
|
1130
|
+
}
|
|
1131
|
+
|
|
1132
|
+
async function executeTools<TOOLS extends ToolSet>({
|
|
1133
|
+
toolCalls,
|
|
1134
|
+
tools,
|
|
1135
|
+
telemetry,
|
|
1136
|
+
callId,
|
|
1137
|
+
messages,
|
|
1138
|
+
abortSignal,
|
|
1139
|
+
timeout,
|
|
1140
|
+
experimental_context,
|
|
1141
|
+
stepNumber,
|
|
1142
|
+
provider,
|
|
1143
|
+
modelId,
|
|
1144
|
+
onToolCallStart,
|
|
1145
|
+
onToolCallFinish,
|
|
1146
|
+
executeToolInTelemetryContext,
|
|
1147
|
+
}: {
|
|
1148
|
+
toolCalls: Array<TypedToolCall<TOOLS>>;
|
|
1149
|
+
tools: TOOLS;
|
|
1150
|
+
telemetry: TelemetrySettings | undefined;
|
|
1151
|
+
callId: string;
|
|
1152
|
+
messages: ModelMessage[];
|
|
1153
|
+
abortSignal: AbortSignal | undefined;
|
|
1154
|
+
timeout?: TimeoutConfiguration<TOOLS>;
|
|
1155
|
+
experimental_context: unknown;
|
|
1156
|
+
stepNumber: number;
|
|
1157
|
+
provider: string;
|
|
1158
|
+
modelId: string;
|
|
1159
|
+
onToolCallStart?: GenerateTextOnToolCallStartCallback<TOOLS>;
|
|
1160
|
+
onToolCallFinish?: GenerateTextOnToolCallFinishCallback<TOOLS>;
|
|
1161
|
+
executeToolInTelemetryContext?: TelemetryIntegration['executeTool'];
|
|
1162
|
+
}): Promise<Array<ToolOutput<TOOLS>>> {
|
|
1163
|
+
const toolOutputs = await Promise.all(
|
|
1164
|
+
toolCalls.map(async toolCall =>
|
|
1165
|
+
executeToolCall({
|
|
1166
|
+
toolCall,
|
|
1167
|
+
tools,
|
|
1168
|
+
telemetry,
|
|
1169
|
+
callId,
|
|
1170
|
+
messages,
|
|
1171
|
+
abortSignal,
|
|
1172
|
+
timeout,
|
|
1173
|
+
experimental_context,
|
|
1174
|
+
stepNumber,
|
|
1175
|
+
provider,
|
|
1176
|
+
modelId,
|
|
1177
|
+
onToolCallStart,
|
|
1178
|
+
onToolCallFinish,
|
|
1179
|
+
executeToolInTelemetryContext,
|
|
1180
|
+
}),
|
|
1181
|
+
),
|
|
1182
|
+
);
|
|
1183
|
+
|
|
1184
|
+
return toolOutputs.filter(
|
|
1185
|
+
(output): output is NonNullable<typeof output> => output != null,
|
|
1186
|
+
);
|
|
1187
|
+
}
|
|
1188
|
+
|
|
1189
|
+
class DefaultGenerateTextResult<
|
|
1190
|
+
TOOLS extends ToolSet,
|
|
1191
|
+
OUTPUT extends Output,
|
|
1192
|
+
> implements GenerateTextResult<TOOLS, OUTPUT> {
|
|
1193
|
+
readonly steps: GenerateTextResult<TOOLS, OUTPUT>['steps'];
|
|
1194
|
+
readonly totalUsage: LanguageModelUsage;
|
|
1195
|
+
private readonly _output: InferCompleteOutput<OUTPUT> | undefined;
|
|
1196
|
+
|
|
1197
|
+
constructor(options: {
|
|
1198
|
+
steps: GenerateTextResult<TOOLS, OUTPUT>['steps'];
|
|
1199
|
+
output: InferCompleteOutput<OUTPUT> | undefined;
|
|
1200
|
+
totalUsage: LanguageModelUsage;
|
|
1201
|
+
}) {
|
|
1202
|
+
this.steps = options.steps;
|
|
1203
|
+
this._output = options.output;
|
|
1204
|
+
this.totalUsage = options.totalUsage;
|
|
1205
|
+
}
|
|
1206
|
+
|
|
1207
|
+
private get finalStep() {
|
|
1208
|
+
return this.steps[this.steps.length - 1];
|
|
1209
|
+
}
|
|
1210
|
+
|
|
1211
|
+
get content() {
|
|
1212
|
+
return this.finalStep.content;
|
|
1213
|
+
}
|
|
1214
|
+
|
|
1215
|
+
get text() {
|
|
1216
|
+
return this.finalStep.text;
|
|
1217
|
+
}
|
|
1218
|
+
|
|
1219
|
+
get files() {
|
|
1220
|
+
return this.finalStep.files;
|
|
1221
|
+
}
|
|
1222
|
+
|
|
1223
|
+
get reasoningText() {
|
|
1224
|
+
return this.finalStep.reasoningText;
|
|
1225
|
+
}
|
|
1226
|
+
|
|
1227
|
+
get reasoning() {
|
|
1228
|
+
return convertToReasoningOutputs(this.finalStep.reasoning);
|
|
1229
|
+
}
|
|
1230
|
+
|
|
1231
|
+
get toolCalls() {
|
|
1232
|
+
return this.finalStep.toolCalls;
|
|
1233
|
+
}
|
|
1234
|
+
|
|
1235
|
+
get staticToolCalls() {
|
|
1236
|
+
return this.finalStep.staticToolCalls;
|
|
1237
|
+
}
|
|
1238
|
+
|
|
1239
|
+
get dynamicToolCalls() {
|
|
1240
|
+
return this.finalStep.dynamicToolCalls;
|
|
1241
|
+
}
|
|
1242
|
+
|
|
1243
|
+
get toolResults() {
|
|
1244
|
+
return this.finalStep.toolResults;
|
|
1245
|
+
}
|
|
1246
|
+
|
|
1247
|
+
get staticToolResults() {
|
|
1248
|
+
return this.finalStep.staticToolResults;
|
|
1249
|
+
}
|
|
1250
|
+
|
|
1251
|
+
get dynamicToolResults() {
|
|
1252
|
+
return this.finalStep.dynamicToolResults;
|
|
1253
|
+
}
|
|
1254
|
+
|
|
1255
|
+
get sources() {
|
|
1256
|
+
return this.finalStep.sources;
|
|
1257
|
+
}
|
|
1258
|
+
|
|
1259
|
+
get finishReason() {
|
|
1260
|
+
return this.finalStep.finishReason;
|
|
1261
|
+
}
|
|
1262
|
+
|
|
1263
|
+
get rawFinishReason() {
|
|
1264
|
+
return this.finalStep.rawFinishReason;
|
|
1265
|
+
}
|
|
1266
|
+
|
|
1267
|
+
get warnings() {
|
|
1268
|
+
return this.finalStep.warnings;
|
|
1269
|
+
}
|
|
1270
|
+
|
|
1271
|
+
get providerMetadata() {
|
|
1272
|
+
return this.finalStep.providerMetadata;
|
|
1273
|
+
}
|
|
1274
|
+
|
|
1275
|
+
get response() {
|
|
1276
|
+
return this.finalStep.response;
|
|
1277
|
+
}
|
|
1278
|
+
|
|
1279
|
+
get request() {
|
|
1280
|
+
return this.finalStep.request;
|
|
1281
|
+
}
|
|
1282
|
+
|
|
1283
|
+
get usage() {
|
|
1284
|
+
return this.finalStep.usage;
|
|
1285
|
+
}
|
|
1286
|
+
|
|
1287
|
+
get experimental_output() {
|
|
1288
|
+
return this.output;
|
|
1289
|
+
}
|
|
1290
|
+
|
|
1291
|
+
get output() {
|
|
1292
|
+
if (this._output == null) {
|
|
1293
|
+
throw new NoOutputGeneratedError();
|
|
1294
|
+
}
|
|
1295
|
+
|
|
1296
|
+
return this._output;
|
|
1297
|
+
}
|
|
1298
|
+
}
|
|
1299
|
+
|
|
1300
|
+
function asContent<TOOLS extends ToolSet>({
|
|
1301
|
+
content,
|
|
1302
|
+
toolCalls,
|
|
1303
|
+
toolOutputs,
|
|
1304
|
+
toolApprovalRequests,
|
|
1305
|
+
tools,
|
|
1306
|
+
}: {
|
|
1307
|
+
content: Array<LanguageModelV4Content>;
|
|
1308
|
+
toolCalls: Array<TypedToolCall<TOOLS>>;
|
|
1309
|
+
toolOutputs: Array<ToolOutput<TOOLS>>;
|
|
1310
|
+
toolApprovalRequests: Array<ToolApprovalRequestOutput<TOOLS>>;
|
|
1311
|
+
tools: TOOLS | undefined;
|
|
1312
|
+
}): Array<ContentPart<TOOLS>> {
|
|
1313
|
+
const contentParts: Array<ContentPart<TOOLS>> = [];
|
|
1314
|
+
|
|
1315
|
+
for (const part of content) {
|
|
1316
|
+
switch (part.type) {
|
|
1317
|
+
case 'text':
|
|
1318
|
+
case 'reasoning':
|
|
1319
|
+
case 'custom':
|
|
1320
|
+
case 'source':
|
|
1321
|
+
contentParts.push(part);
|
|
1322
|
+
break;
|
|
1323
|
+
|
|
1324
|
+
case 'file':
|
|
1325
|
+
case 'reasoning-file': {
|
|
1326
|
+
contentParts.push({
|
|
1327
|
+
type: part.type as 'file' | 'reasoning-file',
|
|
1328
|
+
file: new DefaultGeneratedFile(part),
|
|
1329
|
+
...(part.providerMetadata != null
|
|
1330
|
+
? { providerMetadata: part.providerMetadata }
|
|
1331
|
+
: {}),
|
|
1332
|
+
});
|
|
1333
|
+
break;
|
|
1334
|
+
}
|
|
1335
|
+
|
|
1336
|
+
case 'tool-call': {
|
|
1337
|
+
contentParts.push(
|
|
1338
|
+
toolCalls.find(toolCall => toolCall.toolCallId === part.toolCallId)!,
|
|
1339
|
+
);
|
|
1340
|
+
break;
|
|
1341
|
+
}
|
|
1342
|
+
|
|
1343
|
+
case 'tool-result': {
|
|
1344
|
+
const toolCall = toolCalls.find(
|
|
1345
|
+
toolCall => toolCall.toolCallId === part.toolCallId,
|
|
1346
|
+
);
|
|
1347
|
+
|
|
1348
|
+
// Handle deferred results for provider-executed tools (e.g., programmatic tool calling).
|
|
1349
|
+
// When a server tool (like code_execution) triggers a client tool, the server tool's
|
|
1350
|
+
// result may be deferred to a later turn. In this case, there's no matching tool-call
|
|
1351
|
+
// in the current response.
|
|
1352
|
+
if (toolCall == null) {
|
|
1353
|
+
const tool = tools?.[part.toolName];
|
|
1354
|
+
const supportsDeferredResults =
|
|
1355
|
+
tool?.type === 'provider' && tool.supportsDeferredResults;
|
|
1356
|
+
|
|
1357
|
+
if (!supportsDeferredResults) {
|
|
1358
|
+
throw new Error(`Tool call ${part.toolCallId} not found.`);
|
|
1359
|
+
}
|
|
1360
|
+
|
|
1361
|
+
// Create tool result without tool call input (deferred result)
|
|
1362
|
+
if (part.isError) {
|
|
1363
|
+
contentParts.push({
|
|
1364
|
+
type: 'tool-error' as const,
|
|
1365
|
+
toolCallId: part.toolCallId,
|
|
1366
|
+
toolName: part.toolName as keyof TOOLS & string,
|
|
1367
|
+
input: undefined,
|
|
1368
|
+
error: part.result,
|
|
1369
|
+
providerExecuted: true,
|
|
1370
|
+
dynamic: part.dynamic,
|
|
1371
|
+
...(part.providerMetadata != null
|
|
1372
|
+
? { providerMetadata: part.providerMetadata }
|
|
1373
|
+
: {}),
|
|
1374
|
+
} as TypedToolError<TOOLS>);
|
|
1375
|
+
} else {
|
|
1376
|
+
contentParts.push({
|
|
1377
|
+
type: 'tool-result' as const,
|
|
1378
|
+
toolCallId: part.toolCallId,
|
|
1379
|
+
toolName: part.toolName as keyof TOOLS & string,
|
|
1380
|
+
input: undefined,
|
|
1381
|
+
output: part.result,
|
|
1382
|
+
providerExecuted: true,
|
|
1383
|
+
dynamic: part.dynamic,
|
|
1384
|
+
...(part.providerMetadata != null
|
|
1385
|
+
? { providerMetadata: part.providerMetadata }
|
|
1386
|
+
: {}),
|
|
1387
|
+
} as TypedToolResult<TOOLS>);
|
|
1388
|
+
}
|
|
1389
|
+
break;
|
|
1390
|
+
}
|
|
1391
|
+
|
|
1392
|
+
if (part.isError) {
|
|
1393
|
+
contentParts.push({
|
|
1394
|
+
type: 'tool-error' as const,
|
|
1395
|
+
toolCallId: part.toolCallId,
|
|
1396
|
+
toolName: part.toolName as keyof TOOLS & string,
|
|
1397
|
+
input: toolCall.input,
|
|
1398
|
+
error: part.result,
|
|
1399
|
+
providerExecuted: true,
|
|
1400
|
+
dynamic: toolCall.dynamic,
|
|
1401
|
+
...(part.providerMetadata != null
|
|
1402
|
+
? { providerMetadata: part.providerMetadata }
|
|
1403
|
+
: {}),
|
|
1404
|
+
} as TypedToolError<TOOLS>);
|
|
1405
|
+
} else {
|
|
1406
|
+
contentParts.push({
|
|
1407
|
+
type: 'tool-result' as const,
|
|
1408
|
+
toolCallId: part.toolCallId,
|
|
1409
|
+
toolName: part.toolName as keyof TOOLS & string,
|
|
1410
|
+
input: toolCall.input,
|
|
1411
|
+
output: part.result,
|
|
1412
|
+
providerExecuted: true,
|
|
1413
|
+
dynamic: toolCall.dynamic,
|
|
1414
|
+
...(part.providerMetadata != null
|
|
1415
|
+
? { providerMetadata: part.providerMetadata }
|
|
1416
|
+
: {}),
|
|
1417
|
+
} as TypedToolResult<TOOLS>);
|
|
1418
|
+
}
|
|
1419
|
+
break;
|
|
1420
|
+
}
|
|
1421
|
+
|
|
1422
|
+
case 'tool-approval-request': {
|
|
1423
|
+
const toolCall = toolCalls.find(
|
|
1424
|
+
toolCall => toolCall.toolCallId === part.toolCallId,
|
|
1425
|
+
);
|
|
1426
|
+
|
|
1427
|
+
if (toolCall == null) {
|
|
1428
|
+
throw new ToolCallNotFoundForApprovalError({
|
|
1429
|
+
toolCallId: part.toolCallId,
|
|
1430
|
+
approvalId: part.approvalId,
|
|
1431
|
+
});
|
|
1432
|
+
}
|
|
1433
|
+
|
|
1434
|
+
contentParts.push({
|
|
1435
|
+
type: 'tool-approval-request' as const,
|
|
1436
|
+
approvalId: part.approvalId,
|
|
1437
|
+
toolCall,
|
|
1438
|
+
});
|
|
1439
|
+
break;
|
|
1440
|
+
}
|
|
1441
|
+
}
|
|
1442
|
+
}
|
|
1443
|
+
|
|
1444
|
+
return [...contentParts, ...toolOutputs, ...toolApprovalRequests];
|
|
1445
|
+
}
|