ai 7.0.0-beta.113 → 7.0.0-beta.115

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.
Files changed (236) hide show
  1. package/CHANGELOG.md +32 -0
  2. package/dist/index.d.ts +1506 -1468
  3. package/dist/index.js +889 -979
  4. package/dist/index.js.map +1 -1
  5. package/dist/internal/index.d.ts +273 -273
  6. package/dist/internal/index.js +367 -405
  7. package/dist/internal/index.js.map +1 -1
  8. package/dist/test/index.d.ts +18 -18
  9. package/dist/test/index.js +22 -22
  10. package/dist/test/index.js.map +1 -1
  11. package/docs/02-foundations/03-prompts.mdx +13 -11
  12. package/docs/03-ai-sdk-core/15-tools-and-tool-calling.mdx +2 -1
  13. package/docs/03-ai-sdk-core/39-file-uploads.mdx +1 -1
  14. package/docs/03-ai-sdk-core/45-provider-management.mdx +1 -1
  15. package/docs/03-ai-sdk-core/60-telemetry.mdx +87 -13
  16. package/docs/07-reference/01-ai-sdk-core/12-generate-speech.mdx +2 -2
  17. package/docs/07-reference/01-ai-sdk-core/20-tool.mdx +7 -0
  18. package/docs/07-reference/01-ai-sdk-core/22-dynamic-tool.mdx +7 -0
  19. package/docs/07-reference/01-ai-sdk-core/30-model-message.mdx +9 -1
  20. package/docs/07-reference/01-ai-sdk-core/40-provider-registry.mdx +104 -0
  21. package/docs/07-reference/01-ai-sdk-core/42-custom-provider.mdx +56 -10
  22. package/docs/07-reference/02-ai-sdk-ui/31-convert-to-model-messages.mdx +1 -1
  23. package/docs/08-migration-guides/23-migration-guide-7-0.mdx +42 -0
  24. package/docs/09-troubleshooting/70-high-memory-usage-with-images.mdx +2 -2
  25. package/package.json +5 -5
  26. package/src/agent/agent.ts +13 -9
  27. package/src/agent/create-agent-ui-stream-response.ts +8 -8
  28. package/src/agent/create-agent-ui-stream.ts +9 -9
  29. package/src/agent/infer-agent-tools.ts +1 -1
  30. package/src/agent/infer-agent-ui-message.ts +2 -2
  31. package/src/agent/pipe-agent-ui-stream-to-response.ts +9 -9
  32. package/src/agent/tool-loop-agent-settings.ts +17 -19
  33. package/src/agent/tool-loop-agent.ts +16 -8
  34. package/src/embed/embed-many-result.ts +3 -4
  35. package/src/embed/embed-many.ts +5 -5
  36. package/src/embed/embed-result.ts +3 -4
  37. package/src/embed/embed.ts +4 -4
  38. package/src/error/invalid-stream-part-error.ts +1 -1
  39. package/src/error/no-image-generated-error.ts +1 -1
  40. package/src/error/no-object-generated-error.ts +3 -3
  41. package/src/error/no-speech-generated-error.ts +1 -1
  42. package/src/error/no-transcript-generated-error.ts +1 -1
  43. package/src/error/no-video-generated-error.ts +1 -1
  44. package/src/error/tool-call-repair-error.ts +2 -2
  45. package/src/error/verify-no-object-generated-error.ts +1 -1
  46. package/src/generate-image/generate-image-result.ts +5 -5
  47. package/src/generate-image/generate-image.ts +12 -15
  48. package/src/generate-image/index.ts +3 -2
  49. package/src/generate-object/generate-object-result.ts +2 -2
  50. package/src/generate-object/generate-object.ts +14 -14
  51. package/src/generate-object/inject-json-instruction.ts +1 -1
  52. package/src/generate-object/output-strategy.ts +10 -10
  53. package/src/generate-object/parse-and-validate-object-result.ts +1 -1
  54. package/src/generate-object/repair-text.ts +1 -1
  55. package/src/generate-object/stream-object-result.ts +4 -4
  56. package/src/generate-object/stream-object.ts +22 -19
  57. package/src/generate-object/validate-object-generation-input.ts +1 -1
  58. package/src/generate-speech/generate-speech-result.ts +4 -4
  59. package/src/generate-speech/generate-speech.ts +12 -13
  60. package/src/generate-speech/generated-audio-file.ts +1 -2
  61. package/src/generate-text/collect-tool-approvals.ts +4 -4
  62. package/src/generate-text/content-part.ts +9 -9
  63. package/src/generate-text/create-execute-tools-transformation.ts +9 -7
  64. package/src/generate-text/execute-tool-call.ts +11 -13
  65. package/src/generate-text/extract-reasoning-content.ts +1 -1
  66. package/src/generate-text/extract-text-content.ts +4 -1
  67. package/src/generate-text/generate-text-events.ts +2 -2
  68. package/src/generate-text/generate-text-result.ts +18 -14
  69. package/src/generate-text/generate-text.ts +42 -38
  70. package/src/generate-text/invoke-tool-callbacks-from-stream.ts +2 -3
  71. package/src/generate-text/output-utils.ts +1 -1
  72. package/src/generate-text/output.ts +8 -8
  73. package/src/generate-text/parse-tool-call.ts +36 -9
  74. package/src/generate-text/prepare-step.ts +3 -5
  75. package/src/generate-text/prune-messages.ts +1 -1
  76. package/src/generate-text/reasoning-output.ts +26 -9
  77. package/src/generate-text/reasoning.ts +1 -1
  78. package/src/generate-text/resolve-tool-approval.ts +3 -3
  79. package/src/generate-text/response-message.ts +1 -1
  80. package/src/generate-text/restricted-telemetry-dispatcher.ts +1 -1
  81. package/src/generate-text/smooth-stream.ts +6 -5
  82. package/src/generate-text/step-result.ts +16 -11
  83. package/src/generate-text/stop-condition.ts +1 -1
  84. package/src/generate-text/stream-language-model-call.ts +26 -21
  85. package/src/generate-text/stream-text-result.ts +29 -26
  86. package/src/generate-text/stream-text.ts +48 -46
  87. package/src/generate-text/to-response-messages.ts +2 -2
  88. package/src/generate-text/tool-approval-configuration.ts +2 -2
  89. package/src/generate-text/tool-approval-request-output.ts +1 -1
  90. package/src/generate-text/tool-approval-response-output.ts +1 -1
  91. package/src/generate-text/tool-call-repair-function.ts +4 -4
  92. package/src/generate-text/tool-call.ts +3 -4
  93. package/src/generate-text/tool-error.ts +3 -4
  94. package/src/generate-text/tool-execution-events.ts +2 -2
  95. package/src/generate-text/tool-output-denied.ts +1 -1
  96. package/src/generate-text/tool-output.ts +2 -2
  97. package/src/generate-text/tool-result.ts +7 -4
  98. package/src/generate-text/tools-context-parameter.ts +1 -1
  99. package/src/generate-text/validate-tool-context.ts +1 -2
  100. package/src/generate-video/generate-video-result.ts +4 -4
  101. package/src/generate-video/generate-video.ts +6 -10
  102. package/src/global.ts +2 -2
  103. package/src/index.ts +3 -3
  104. package/src/logger/log-warnings.ts +1 -1
  105. package/src/middleware/add-tool-input-examples-middleware.ts +2 -2
  106. package/src/middleware/default-embedding-settings-middleware.ts +2 -2
  107. package/src/middleware/default-settings-middleware.ts +2 -2
  108. package/src/middleware/extract-json-middleware.ts +1 -1
  109. package/src/middleware/extract-reasoning-middleware.ts +1 -1
  110. package/src/middleware/simulate-streaming-middleware.ts +1 -1
  111. package/src/middleware/wrap-embedding-model.ts +2 -2
  112. package/src/middleware/wrap-image-model.ts +2 -2
  113. package/src/middleware/wrap-language-model.ts +2 -2
  114. package/src/middleware/wrap-provider.ts +2 -2
  115. package/src/model/as-embedding-model-v3.ts +1 -1
  116. package/src/model/as-embedding-model-v4.ts +1 -1
  117. package/src/model/as-image-model-v3.ts +1 -1
  118. package/src/model/as-image-model-v4.ts +5 -1
  119. package/src/model/as-language-model-v3.ts +1 -1
  120. package/src/model/as-language-model-v4.ts +1 -1
  121. package/src/model/as-provider-v3.ts +1 -1
  122. package/src/model/as-provider-v4.ts +1 -1
  123. package/src/model/as-reranking-model-v4.ts +1 -1
  124. package/src/model/as-speech-model-v3.ts +1 -1
  125. package/src/model/as-speech-model-v4.ts +5 -1
  126. package/src/model/as-transcription-model-v3.ts +4 -1
  127. package/src/model/as-transcription-model-v4.ts +1 -1
  128. package/src/model/as-video-model-v4.ts +1 -1
  129. package/src/model/resolve-model.ts +8 -8
  130. package/src/prompt/content-part.ts +45 -15
  131. package/src/prompt/convert-to-language-model-prompt.ts +108 -122
  132. package/src/prompt/create-tool-model-output.ts +2 -2
  133. package/src/prompt/data-content.ts +1 -78
  134. package/src/prompt/file-part-data.ts +125 -0
  135. package/src/prompt/index.ts +3 -2
  136. package/src/prompt/language-model-call-options.ts +1 -1
  137. package/src/prompt/message-conversion-error.ts +1 -1
  138. package/src/prompt/message.ts +1 -1
  139. package/src/prompt/prepare-language-model-call-options.ts +1 -1
  140. package/src/prompt/prepare-tool-choice.ts +2 -2
  141. package/src/prompt/prepare-tools.ts +2 -2
  142. package/src/prompt/prompt.ts +1 -1
  143. package/src/prompt/standardize-prompt.ts +3 -3
  144. package/src/registry/custom-provider.ts +127 -92
  145. package/src/registry/index.ts +1 -1
  146. package/src/registry/provider-registry.ts +91 -87
  147. package/src/rerank/rerank-result.ts +1 -1
  148. package/src/rerank/rerank.ts +8 -5
  149. package/src/telemetry/create-telemetry-dispatcher.ts +11 -1
  150. package/src/telemetry/diagnostic-channel-publisher.ts +50 -0
  151. package/src/telemetry/diagnostic-channel.ts +24 -0
  152. package/src/telemetry/index.ts +5 -0
  153. package/src/telemetry/telemetry.ts +1 -1
  154. package/src/test/mock-embedding-model-v2.ts +1 -1
  155. package/src/test/mock-embedding-model-v3.ts +1 -1
  156. package/src/test/mock-embedding-model-v4.ts +1 -1
  157. package/src/test/mock-image-model-v2.ts +1 -1
  158. package/src/test/mock-image-model-v3.ts +1 -1
  159. package/src/test/mock-image-model-v4.ts +1 -1
  160. package/src/test/mock-language-model-v2.ts +1 -1
  161. package/src/test/mock-language-model-v3.ts +1 -1
  162. package/src/test/mock-language-model-v4.ts +1 -1
  163. package/src/test/mock-provider-v2.ts +6 -7
  164. package/src/test/mock-provider-v3.ts +7 -8
  165. package/src/test/mock-provider-v4.ts +7 -8
  166. package/src/test/mock-reranking-model-v3.ts +1 -1
  167. package/src/test/mock-reranking-model-v4.ts +1 -1
  168. package/src/test/mock-server-response.ts +1 -1
  169. package/src/test/mock-speech-model-v2.ts +1 -1
  170. package/src/test/mock-speech-model-v3.ts +1 -1
  171. package/src/test/mock-speech-model-v4.ts +1 -1
  172. package/src/test/mock-transcription-model-v2.ts +1 -1
  173. package/src/test/mock-transcription-model-v3.ts +1 -1
  174. package/src/test/mock-transcription-model-v4.ts +1 -1
  175. package/src/test/mock-video-model-v3.ts +1 -1
  176. package/src/test/mock-video-model-v4.ts +1 -1
  177. package/src/text-stream/pipe-text-stream-to-response.ts +1 -1
  178. package/src/transcribe/transcribe-result.ts +3 -3
  179. package/src/transcribe/transcribe.ts +12 -12
  180. package/src/types/embedding-model-middleware.ts +1 -1
  181. package/src/types/embedding-model.ts +1 -1
  182. package/src/types/image-model-middleware.ts +1 -1
  183. package/src/types/image-model.ts +1 -1
  184. package/src/types/json-value.ts +1 -1
  185. package/src/types/language-model-middleware.ts +1 -1
  186. package/src/types/language-model.ts +2 -2
  187. package/src/types/provider-metadata.ts +1 -1
  188. package/src/types/provider-reference.ts +1 -1
  189. package/src/types/provider.ts +4 -4
  190. package/src/types/reranking-model.ts +1 -1
  191. package/src/types/speech-model.ts +5 -1
  192. package/src/types/transcription-model.ts +1 -1
  193. package/src/types/usage.ts +1 -1
  194. package/src/types/video-model.ts +1 -1
  195. package/src/types/warning.ts +1 -1
  196. package/src/ui/call-completion-api.ts +2 -2
  197. package/src/ui/chat-transport.ts +3 -3
  198. package/src/ui/chat.ts +10 -11
  199. package/src/ui/convert-file-list-to-file-ui-parts.ts +1 -1
  200. package/src/ui/convert-to-model-messages.ts +34 -23
  201. package/src/ui/default-chat-transport.ts +4 -4
  202. package/src/ui/direct-chat-transport.ts +6 -6
  203. package/src/ui/http-chat-transport.ts +5 -5
  204. package/src/ui/last-assistant-message-is-complete-with-approval-responses.ts +0 -1
  205. package/src/ui/last-assistant-message-is-complete-with-tool-calls.ts +0 -1
  206. package/src/ui/process-ui-message-stream.ts +20 -21
  207. package/src/ui/text-stream-chat-transport.ts +3 -3
  208. package/src/ui/transform-text-to-ui-message-stream.ts +1 -1
  209. package/src/ui/ui-messages.ts +13 -6
  210. package/src/ui/use-completion.ts +1 -1
  211. package/src/ui/validate-ui-messages.ts +3 -3
  212. package/src/ui-message-stream/create-ui-message-stream-response.ts +2 -2
  213. package/src/ui-message-stream/create-ui-message-stream.ts +6 -6
  214. package/src/ui-message-stream/get-response-ui-message-id.ts +2 -2
  215. package/src/ui-message-stream/handle-ui-message-stream-finish.ts +6 -6
  216. package/src/ui-message-stream/pipe-ui-message-stream-to-response.ts +3 -3
  217. package/src/ui-message-stream/read-ui-message-stream.ts +4 -4
  218. package/src/ui-message-stream/ui-message-chunks.ts +4 -4
  219. package/src/ui-message-stream/ui-message-stream-on-finish-callback.ts +2 -2
  220. package/src/ui-message-stream/ui-message-stream-on-step-finish-callback.ts +1 -1
  221. package/src/ui-message-stream/ui-message-stream-writer.ts +3 -3
  222. package/src/upload-file/upload-file-result.ts +3 -3
  223. package/src/upload-file/upload-file.ts +34 -56
  224. package/src/upload-skill/upload-skill-result.ts +3 -3
  225. package/src/upload-skill/upload-skill.ts +27 -8
  226. package/src/util/create-resolvable-promise.ts +1 -1
  227. package/src/util/deep-partial.ts +1 -1
  228. package/src/util/download/download.ts +0 -2
  229. package/src/util/extract-literal-union.ts +18 -0
  230. package/src/util/is-node-runtime.ts +3 -0
  231. package/src/util/notify.ts +1 -1
  232. package/src/util/parse-partial-json.ts +1 -1
  233. package/src/util/prepare-retries.ts +1 -2
  234. package/src/util/serial-job-executor.ts +1 -1
  235. package/src/util/write-to-server-response.ts +1 -1
  236. package/src/util/detect-media-type.ts +0 -235
@@ -1,4 +1,8 @@
1
- import { ImageModelV2, ImageModelV3, ImageModelV4 } from '@ai-sdk/provider';
1
+ import type {
2
+ ImageModelV2,
3
+ ImageModelV3,
4
+ ImageModelV4,
5
+ } from '@ai-sdk/provider';
2
6
  import { asImageModelV3 } from './as-image-model-v3';
3
7
 
4
8
  export function asImageModelV4(
@@ -1,4 +1,4 @@
1
- import {
1
+ import type {
2
2
  LanguageModelV2,
3
3
  LanguageModelV2FinishReason,
4
4
  LanguageModelV2StreamPart,
@@ -1,4 +1,4 @@
1
- import {
1
+ import type {
2
2
  LanguageModelV2,
3
3
  LanguageModelV3,
4
4
  LanguageModelV4,
@@ -1,4 +1,4 @@
1
- import { ProviderV2, ProviderV3 } from '@ai-sdk/provider';
1
+ import type { ProviderV2, ProviderV3 } from '@ai-sdk/provider';
2
2
  import { asEmbeddingModelV3 } from './as-embedding-model-v3';
3
3
  import { asImageModelV3 } from './as-image-model-v3';
4
4
  import { asLanguageModelV3 } from './as-language-model-v3';
@@ -1,4 +1,4 @@
1
- import { ProviderV2, ProviderV3, ProviderV4 } from '@ai-sdk/provider';
1
+ import type { ProviderV2, ProviderV3, ProviderV4 } from '@ai-sdk/provider';
2
2
  import { asProviderV3 } from './as-provider-v3';
3
3
  import { asEmbeddingModelV4 } from './as-embedding-model-v4';
4
4
  import { asImageModelV4 } from './as-image-model-v4';
@@ -1,4 +1,4 @@
1
- import { RerankingModelV3, RerankingModelV4 } from '@ai-sdk/provider';
1
+ import type { RerankingModelV3, RerankingModelV4 } from '@ai-sdk/provider';
2
2
 
3
3
  export function asRerankingModelV4(
4
4
  model: RerankingModelV3 | RerankingModelV4,
@@ -1,4 +1,4 @@
1
- import { SpeechModelV2, SpeechModelV3 } from '@ai-sdk/provider';
1
+ import type { SpeechModelV2, SpeechModelV3 } from '@ai-sdk/provider';
2
2
  import { logV2CompatibilityWarning } from '../util/log-v2-compatibility-warning';
3
3
 
4
4
  export function asSpeechModelV3(
@@ -1,4 +1,8 @@
1
- import { SpeechModelV2, SpeechModelV3, SpeechModelV4 } from '@ai-sdk/provider';
1
+ import type {
2
+ SpeechModelV2,
3
+ SpeechModelV3,
4
+ SpeechModelV4,
5
+ } from '@ai-sdk/provider';
2
6
  import { asSpeechModelV3 } from './as-speech-model-v3';
3
7
 
4
8
  export function asSpeechModelV4(
@@ -1,4 +1,7 @@
1
- import { TranscriptionModelV2, TranscriptionModelV3 } from '@ai-sdk/provider';
1
+ import type {
2
+ TranscriptionModelV2,
3
+ TranscriptionModelV3,
4
+ } from '@ai-sdk/provider';
2
5
  import { logV2CompatibilityWarning } from '../util/log-v2-compatibility-warning';
3
6
 
4
7
  export function asTranscriptionModelV3(
@@ -1,4 +1,4 @@
1
- import {
1
+ import type {
2
2
  TranscriptionModelV2,
3
3
  TranscriptionModelV3,
4
4
  TranscriptionModelV4,
@@ -1,4 +1,4 @@
1
- import {
1
+ import type {
2
2
  Experimental_VideoModelV3,
3
3
  Experimental_VideoModelV4,
4
4
  } from '@ai-sdk/provider';
@@ -1,5 +1,5 @@
1
1
  import { gateway } from '@ai-sdk/gateway';
2
- import {
2
+ import type {
3
3
  EmbeddingModelV4,
4
4
  Experimental_VideoModelV4,
5
5
  ImageModelV4,
@@ -10,10 +10,10 @@ import {
10
10
  TranscriptionModelV4,
11
11
  } from '@ai-sdk/provider';
12
12
  import { UnsupportedModelVersionError } from '../error';
13
- import { EmbeddingModel } from '../types/embedding-model';
14
- import { LanguageModel } from '../types/language-model';
15
- import { SpeechModel } from '../types/speech-model';
16
- import { TranscriptionModel } from '../types/transcription-model';
13
+ import type { EmbeddingModel } from '../types/embedding-model';
14
+ import type { LanguageModel } from '../types/language-model';
15
+ import type { SpeechModel } from '../types/speech-model';
16
+ import type { TranscriptionModel } from '../types/transcription-model';
17
17
  import { asEmbeddingModelV4 } from './as-embedding-model-v4';
18
18
  import { asImageModelV4 } from './as-image-model-v4';
19
19
  import { asLanguageModelV4 } from './as-language-model-v4';
@@ -22,9 +22,9 @@ import { asSpeechModelV4 } from './as-speech-model-v4';
22
22
  import { asTranscriptionModelV4 } from './as-transcription-model-v4';
23
23
  import { asVideoModelV4 } from './as-video-model-v4';
24
24
  import { asProviderV4 } from './as-provider-v4';
25
- import { ImageModel } from '../types/image-model';
26
- import { RerankingModel } from '../types/reranking-model';
27
- import { VideoModel } from '../types/video-model';
25
+ import type { ImageModel } from '../types/image-model';
26
+ import type { RerankingModel } from '../types/reranking-model';
27
+ import type { VideoModel } from '../types/video-model';
28
28
 
29
29
  export function resolveLanguageModel(model: LanguageModel): LanguageModelV4 {
30
30
  if (typeof model === 'string') {
@@ -1,20 +1,28 @@
1
1
  import {
2
- CustomPart,
3
- FilePart,
4
- ImagePart,
5
- ProviderOptions,
6
- ReasoningFilePart,
7
- ReasoningPart,
8
- TextPart,
9
- ToolApprovalRequest,
10
- ToolApprovalResponse,
11
- ToolResultOutput,
12
- ToolResultPart,
2
+ isBuffer,
3
+ type CustomPart,
4
+ type DataContent,
5
+ type FilePart,
6
+ type ImagePart,
7
+ type ProviderOptions,
8
+ type ReasoningFilePart,
9
+ type ReasoningPart,
10
+ type TextPart,
11
+ type ToolApprovalRequest,
12
+ type ToolApprovalResponse,
13
+ type ToolResultOutput,
14
+ type ToolResultPart,
13
15
  } from '@ai-sdk/provider-utils';
14
16
  import { z } from 'zod/v4';
15
17
  import { jsonValueSchema } from '../types/json-value';
16
18
  import { providerMetadataSchema } from '../types/provider-metadata';
17
- import { dataContentSchema } from './data-content';
19
+
20
+ const fileInlineDataSchema: z.ZodType<DataContent> = z.union([
21
+ z.string(),
22
+ z.instanceof(Uint8Array),
23
+ z.instanceof(ArrayBuffer),
24
+ z.custom<Buffer>(isBuffer, { message: 'Must be a Buffer' }),
25
+ ]);
18
26
 
19
27
  const providerReferenceSchema = z.record(z.string(), z.string());
20
28
 
@@ -29,11 +37,13 @@ export const textPartSchema: z.ZodType<TextPart> = z.object({
29
37
 
30
38
  /**
31
39
  * @internal
40
+ * @deprecated Use `filePartSchema` with `mediaType: 'image'` instead:
41
+ * `{ type: 'file', mediaType: 'image', data: { type: 'data', data } }`.
32
42
  */
33
43
  export const imagePartSchema: z.ZodType<ImagePart> = z.object({
34
44
  type: z.literal('image'),
35
45
  image: z.union([
36
- dataContentSchema,
46
+ fileInlineDataSchema,
37
47
  z.instanceof(URL),
38
48
  providerReferenceSchema,
39
49
  ]),
@@ -41,13 +51,29 @@ export const imagePartSchema: z.ZodType<ImagePart> = z.object({
41
51
  providerOptions: providerMetadataSchema.optional(),
42
52
  });
43
53
 
54
+ const taggedFileDataSchema = z.discriminatedUnion('type', [
55
+ z.object({ type: z.literal('data'), data: fileInlineDataSchema }),
56
+ z.object({ type: z.literal('url'), url: z.instanceof(URL) }),
57
+ z.object({
58
+ type: z.literal('reference'),
59
+ reference: providerReferenceSchema,
60
+ }),
61
+ z.object({ type: z.literal('text'), text: z.string() }),
62
+ ]);
63
+
64
+ const taggedReasoningFileDataSchema = z.discriminatedUnion('type', [
65
+ z.object({ type: z.literal('data'), data: fileInlineDataSchema }),
66
+ z.object({ type: z.literal('url'), url: z.instanceof(URL) }),
67
+ ]);
68
+
44
69
  /**
45
70
  * @internal
46
71
  */
47
72
  export const filePartSchema: z.ZodType<FilePart> = z.object({
48
73
  type: z.literal('file'),
49
74
  data: z.union([
50
- dataContentSchema,
75
+ taggedFileDataSchema,
76
+ fileInlineDataSchema,
51
77
  z.instanceof(URL),
52
78
  providerReferenceSchema,
53
79
  ]),
@@ -79,7 +105,11 @@ export const customPartSchema: z.ZodType<CustomPart> = z.object({
79
105
  */
80
106
  export const reasoningFilePartSchema: z.ZodType<ReasoningFilePart> = z.object({
81
107
  type: z.literal('reasoning-file'),
82
- data: z.union([dataContentSchema, z.instanceof(URL)]),
108
+ data: z.union([
109
+ taggedReasoningFileDataSchema,
110
+ fileInlineDataSchema,
111
+ z.instanceof(URL),
112
+ ]),
83
113
  mediaType: z.string(),
84
114
  providerOptions: providerMetadataSchema.optional(),
85
115
  });
@@ -1,4 +1,4 @@
1
- import {
1
+ import type {
2
2
  LanguageModelV4FilePart,
3
3
  LanguageModelV4Message,
4
4
  LanguageModelV4Prompt,
@@ -7,33 +7,29 @@ import {
7
7
  } from '@ai-sdk/provider';
8
8
  import {
9
9
  asArray,
10
- CustomPart,
11
- DataContent,
12
- FilePart,
13
- ImagePart,
14
- isProviderReference,
10
+ detectMediaType,
11
+ isFullMediaType,
15
12
  isUrlSupported,
16
- ModelMessage,
17
- ReasoningFilePart,
18
- ReasoningPart,
19
- TextPart,
20
- ToolCallPart,
21
- ToolResultOutput,
22
- ToolResultPart,
13
+ type CustomPart,
14
+ type FilePart,
15
+ type ImagePart,
16
+ type ModelMessage,
17
+ type ReasoningFilePart,
18
+ type ReasoningPart,
19
+ type TextPart,
20
+ type ToolCallPart,
21
+ type ToolResultOutput,
22
+ type ToolResultPart,
23
23
  } from '@ai-sdk/provider-utils';
24
- import {
25
- detectMediaType,
26
- imageMediaTypeSignatures,
27
- } from '../util/detect-media-type';
28
24
  import {
29
25
  createDefaultDownloadFunction,
30
- DownloadFunction,
26
+ type DownloadFunction,
31
27
  } from '../util/download/download-function';
32
- import { convertToLanguageModelV4DataContent } from './data-content';
28
+ import { convertToLanguageModelV4FilePart } from './file-part-data';
33
29
  import { logWarnings } from '../logger/log-warnings';
34
30
  import type { Warning } from '../types/warning';
35
31
  import { InvalidMessageRoleError } from './invalid-message-role-error';
36
- import { StandardizedPrompt } from './standardize-prompt';
32
+ import type { StandardizedPrompt } from './standardize-prompt';
37
33
  import { MissingToolResultsError } from '../error/missing-tool-result-error';
38
34
 
39
35
  export async function convertToLanguageModelPrompt({
@@ -217,6 +213,16 @@ export function convertToLanguageModelMessage({
217
213
  const converted = {
218
214
  role: 'user' as const,
219
215
  content: message.content
216
+ .map(part => {
217
+ if (part.type === 'image') {
218
+ warnings.push({
219
+ type: 'deprecated',
220
+ setting: '"image" content part',
221
+ message: `The "image" content part type is deprecated. Use a "file" part with mediaType: 'image' (or a more specific image/* subtype) instead.`,
222
+ });
223
+ }
224
+ return convertImagePartToFilePart(part);
225
+ })
220
226
  .map(part => convertPartToLanguageModelPart(part, downloadedAssets))
221
227
  // remove empty text parts:
222
228
  .filter(part => part.type !== 'text' || part.text !== ''),
@@ -271,19 +277,7 @@ export function convertToLanguageModelMessage({
271
277
  };
272
278
  }
273
279
  case 'file': {
274
- if (
275
- !(part.data instanceof ArrayBuffer) &&
276
- isProviderReference(part.data)
277
- ) {
278
- return {
279
- type: 'file' as const,
280
- data: part.data,
281
- filename: part.filename,
282
- mediaType: part.mediaType,
283
- providerOptions,
284
- };
285
- }
286
- const { data, mediaType } = convertToLanguageModelV4DataContent(
280
+ const { data, mediaType } = convertToLanguageModelV4FilePart(
287
281
  part.data,
288
282
  );
289
283
  return {
@@ -302,9 +296,14 @@ export function convertToLanguageModelMessage({
302
296
  };
303
297
  }
304
298
  case 'reasoning-file': {
305
- const { data, mediaType } = convertToLanguageModelV4DataContent(
299
+ const { data, mediaType } = convertToLanguageModelV4FilePart(
306
300
  part.data,
307
301
  );
302
+ if (data.type !== 'data' && data.type !== 'url') {
303
+ throw new Error(
304
+ `Unsupported reasoning-file data type: ${data.type}`,
305
+ );
306
+ }
308
307
  return {
309
308
  type: 'reasoning-file' as const,
310
309
  data,
@@ -401,8 +400,29 @@ export function convertToLanguageModelMessage({
401
400
  }
402
401
  }
403
402
 
403
+ /*
404
+ * Rewrites a legacy `ImagePart` into an equivalent `FilePart`. The default
405
+ * `mediaType` for a bare `ImagePart` (no `mediaType`) is `"image"` (top-level
406
+ * segment); an explicit `mediaType` is carried through verbatim. After this
407
+ * pre-pass, only `TextPart` and `FilePart` ever reach the provider-facing
408
+ * conversion logic.
409
+ */
410
+ function convertImagePartToFilePart(
411
+ part: TextPart | ImagePart | FilePart,
412
+ ): TextPart | FilePart {
413
+ if (part.type !== 'image') {
414
+ return part;
415
+ }
416
+ return {
417
+ type: 'file',
418
+ data: part.image,
419
+ mediaType: part.mediaType ?? 'image',
420
+ providerOptions: part.providerOptions,
421
+ };
422
+ }
423
+
404
424
  /**
405
- * Downloads images and files from URLs in the messages.
425
+ * Downloads files from URLs in the user messages.
406
426
  */
407
427
  async function downloadAssets(
408
428
  messages: ModelMessage[],
@@ -411,6 +431,15 @@ async function downloadAssets(
411
431
  ): Promise<
412
432
  Record<string, { mediaType: string | undefined; data: Uint8Array }>
413
433
  > {
434
+ type ConvertedFile = {
435
+ mediaType: string | undefined;
436
+ data: LanguageModelV4FilePart['data'];
437
+ };
438
+ type UrlTaggedFile = {
439
+ mediaType: string | undefined;
440
+ data: { type: 'url'; url: URL };
441
+ };
442
+
414
443
  const plannedDownloads = messages
415
444
  .filter(message => message.role === 'user')
416
445
  .map(message => message.content)
@@ -418,34 +447,20 @@ async function downloadAssets(
418
447
  Array.isArray(content),
419
448
  )
420
449
  .flat()
421
- .filter(
422
- (part): part is ImagePart | FilePart =>
423
- part.type === 'image' || part.type === 'file',
424
- )
425
- .map(part => {
426
- const mediaType =
427
- part.mediaType ?? (part.type === 'image' ? 'image/*' : undefined);
428
-
429
- let data = part.type === 'image' ? part.image : part.data;
430
- if (typeof data === 'string') {
431
- try {
432
- data = new URL(data);
433
- } catch {}
434
- }
435
-
450
+ .map(part => convertImagePartToFilePart(part))
451
+ .filter((part): part is FilePart => part.type === 'file')
452
+ .map((part): ConvertedFile => {
453
+ const mediaType = part.mediaType;
454
+ const { data } = convertToLanguageModelV4FilePart(part.data);
436
455
  return { mediaType, data };
437
456
  })
438
-
439
- .filter(
440
- (part): part is { mediaType: string | undefined; data: URL } =>
441
- part.data instanceof URL,
442
- )
457
+ .filter((part): part is UrlTaggedFile => part.data.type === 'url')
443
458
  .map(part => ({
444
- url: part.data,
459
+ url: part.data.url,
445
460
  isUrlSupportedByModel:
446
461
  part.mediaType != null &&
447
462
  isUrlSupported({
448
- url: part.data.toString(),
463
+ url: part.data.url.toString(),
449
464
  mediaType: part.mediaType,
450
465
  supportedUrls,
451
466
  }),
@@ -469,7 +484,7 @@ async function downloadAssets(
469
484
  }
470
485
 
471
486
  /**
472
- * Convert part of a message to a LanguageModelV4Part.
487
+ * Convert part of a user message to a LanguageModelV4Part.
473
488
  *
474
489
  * @param part - The part to convert.
475
490
  * @param downloadedAssets - A map of URLs to their downloaded data. Only
@@ -477,7 +492,7 @@ async function downloadAssets(
477
492
  * @returns The converted part.
478
493
  */
479
494
  function convertPartToLanguageModelPart(
480
- part: TextPart | ImagePart | FilePart,
495
+ part: TextPart | FilePart,
481
496
  downloadedAssets: Record<
482
497
  string,
483
498
  { mediaType: string | undefined; data: Uint8Array }
@@ -491,78 +506,49 @@ function convertPartToLanguageModelPart(
491
506
  };
492
507
  }
493
508
 
494
- const type = part.type;
495
- const rawData = type === 'image' ? part.image : part.data;
509
+ const { data: normalizedData, mediaType: dataUrlMediaType } =
510
+ convertToLanguageModelV4FilePart(part.data);
496
511
 
497
- if (
498
- typeof rawData === 'object' &&
499
- !(rawData instanceof Uint8Array) &&
500
- !(rawData instanceof ArrayBuffer) &&
501
- !(rawData instanceof URL)
502
- ) {
503
- return {
504
- type: 'file',
505
- mediaType: part.mediaType ?? (type === 'image' ? 'image/*' : ''),
506
- filename: type === 'file' ? part.filename : undefined,
507
- data: rawData,
508
- providerOptions: part.providerOptions,
509
- };
510
- }
511
-
512
- const originalData: DataContent | URL = rawData;
512
+ let mediaType: string | undefined = dataUrlMediaType ?? part.mediaType;
513
+ let data: LanguageModelV4FilePart['data'] = normalizedData;
513
514
 
514
- const { data: convertedData, mediaType: convertedMediaType } =
515
- convertToLanguageModelV4DataContent(originalData);
516
-
517
- let mediaType: string | undefined = convertedMediaType ?? part.mediaType;
518
- let data: Uint8Array | string | URL = convertedData; // binary | base64 | url
519
-
520
- // If the content is a URL, we check if it was downloaded:
521
- if (data instanceof URL) {
522
- const downloadedFile = downloadedAssets[data.toString()];
515
+ if (data.type === 'url') {
516
+ const downloadedFile = downloadedAssets[data.url.toString()];
523
517
  if (downloadedFile) {
524
- data = downloadedFile.data;
525
- mediaType ??= downloadedFile.mediaType;
518
+ data = { type: 'data', data: downloadedFile.data };
519
+ if (
520
+ downloadedFile.mediaType != null &&
521
+ (mediaType == null || !isFullMediaType(mediaType))
522
+ ) {
523
+ mediaType = downloadedFile.mediaType;
524
+ }
526
525
  }
527
526
  }
528
527
 
529
- // Now that we have the normalized data either as a URL or a Uint8Array,
530
- // we can create the LanguageModelV4Part.
531
- switch (type) {
532
- case 'image': {
533
- // When possible, try to detect the media type automatically
534
- // to deal with incorrect media type inputs.
535
- // When detection fails, use provided media type.
536
- if (data instanceof Uint8Array || typeof data === 'string') {
537
- mediaType =
538
- detectMediaType({ data, signatures: imageMediaTypeSignatures }) ??
539
- mediaType;
540
- }
541
-
542
- return {
543
- type: 'file',
544
- mediaType: mediaType ?? 'image/*', // any image
545
- filename: undefined,
546
- data,
547
- providerOptions: part.providerOptions,
548
- };
528
+ if (
529
+ data.type === 'data' &&
530
+ (data.data instanceof Uint8Array || typeof data.data === 'string')
531
+ ) {
532
+ const imageMediaType = detectMediaType({
533
+ data: data.data,
534
+ topLevelType: 'image',
535
+ });
536
+ if (imageMediaType != null) {
537
+ mediaType = imageMediaType;
549
538
  }
539
+ }
550
540
 
551
- case 'file': {
552
- // We must have a mediaType for files, if not, throw an error.
553
- if (mediaType == null) {
554
- throw new Error(`Media type is missing for file part`);
555
- }
556
-
557
- return {
558
- type: 'file',
559
- mediaType,
560
- filename: part.filename,
561
- data,
562
- providerOptions: part.providerOptions,
563
- };
564
- }
541
+ if (mediaType == null) {
542
+ throw new Error(`Media type is missing for file part`);
565
543
  }
544
+
545
+ return {
546
+ type: 'file',
547
+ mediaType,
548
+ filename: part.filename,
549
+ data,
550
+ providerOptions: part.providerOptions,
551
+ };
566
552
  }
567
553
 
568
554
  function mapToolResultOutput({
@@ -1,5 +1,5 @@
1
- import { getErrorMessage, JSONValue } from '@ai-sdk/provider';
2
- import { Tool, ToolResultOutput } from '@ai-sdk/provider-utils';
1
+ import { getErrorMessage, type JSONValue } from '@ai-sdk/provider';
2
+ import type { Tool, ToolResultOutput } from '@ai-sdk/provider-utils';
3
3
 
4
4
  export async function createToolModelOutput({
5
5
  toolCallId,
@@ -1,72 +1,9 @@
1
- import { AISDKError, LanguageModelV4DataContent } from '@ai-sdk/provider';
2
1
  import {
3
2
  convertBase64ToUint8Array,
4
3
  convertUint8ArrayToBase64,
5
- DataContent,
4
+ type DataContent,
6
5
  } from '@ai-sdk/provider-utils';
7
- import { z } from 'zod/v4';
8
6
  import { InvalidDataContentError } from './invalid-data-content-error';
9
- import { splitDataUrl } from './split-data-url';
10
-
11
- /**
12
- * @internal
13
- */
14
- export const dataContentSchema: z.ZodType<DataContent> = z.union([
15
- z.string(),
16
- z.instanceof(Uint8Array),
17
- z.instanceof(ArrayBuffer),
18
- z.custom<Buffer>(
19
- // Buffer might not be available in some environments such as CloudFlare:
20
- (value: unknown): value is Buffer =>
21
- globalThis.Buffer?.isBuffer(value) ?? false,
22
- { message: 'Must be a Buffer' },
23
- ),
24
- ]);
25
-
26
- export function convertToLanguageModelV4DataContent(
27
- content: DataContent | URL,
28
- ): {
29
- data: LanguageModelV4DataContent;
30
- mediaType: string | undefined;
31
- } {
32
- // Buffer & Uint8Array:
33
- if (content instanceof Uint8Array) {
34
- return { data: content, mediaType: undefined };
35
- }
36
-
37
- // ArrayBuffer needs conversion to Uint8Array (lightweight):
38
- if (content instanceof ArrayBuffer) {
39
- return { data: new Uint8Array(content), mediaType: undefined };
40
- }
41
-
42
- // Attempt to create a URL from the data. If it fails, we can assume the data
43
- // is not a URL and likely some other sort of data.
44
- if (typeof content === 'string') {
45
- try {
46
- content = new URL(content);
47
- } catch {
48
- // ignored
49
- }
50
- }
51
-
52
- // Extract data from data URL:
53
- if (content instanceof URL && content.protocol === 'data:') {
54
- const { mediaType: dataUrlMediaType, base64Content } = splitDataUrl(
55
- content.toString(),
56
- );
57
-
58
- if (dataUrlMediaType == null || base64Content == null) {
59
- throw new AISDKError({
60
- name: 'InvalidDataContentError',
61
- message: `Invalid data URL format in content ${content.toString()}`,
62
- });
63
- }
64
-
65
- return { data: base64Content, mediaType: dataUrlMediaType };
66
- }
67
-
68
- return { data: content, mediaType: undefined };
69
- }
70
7
 
71
8
  /**
72
9
  * Converts data content to a base64-encoded string.
@@ -118,17 +55,3 @@ export function convertDataContentToUint8Array(
118
55
 
119
56
  throw new InvalidDataContentError({ content });
120
57
  }
121
-
122
- /**
123
- * Converts a Uint8Array to a string of text.
124
- *
125
- * @param uint8Array - The Uint8Array to convert.
126
- * @returns The converted string.
127
- */
128
- export function convertUint8ArrayToText(uint8Array: Uint8Array): string {
129
- try {
130
- return new TextDecoder().decode(uint8Array);
131
- } catch {
132
- throw new Error('Error decoding Uint8Array to text');
133
- }
134
- }