@ai-sdk/xai 3.0.105 → 3.0.107

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/docs/01-xai.mdx CHANGED
@@ -73,10 +73,10 @@ You can use the following optional settings to customize the xAI provider instan
73
73
  ## Language Models
74
74
 
75
75
  You can create [xAI models](https://console.x.ai) using a provider instance. The
76
- first argument is the model id, e.g. `grok-4.20-non-reasoning`.
76
+ first argument is the model id, e.g. `grok-4.5`.
77
77
 
78
78
  ```ts
79
- const model = xai('grok-4.20-non-reasoning');
79
+ const model = xai('grok-4.5');
80
80
  ```
81
81
 
82
82
  By default, `xai(modelId)` uses the Chat API. To use the Responses API with server-side agentic tools, explicitly use `xai.responses(modelId)`.
@@ -90,7 +90,7 @@ import { xai } from '@ai-sdk/xai';
90
90
  import { generateText } from 'ai';
91
91
 
92
92
  const { text } = await generateText({
93
- model: xai('grok-4.20-non-reasoning'),
93
+ model: xai('grok-4.5'),
94
94
  prompt: 'Write a vegetarian lasagna recipe for 4 people.',
95
95
  });
96
96
  ```
@@ -149,7 +149,7 @@ The following optional provider options are available for xAI chat models:
149
149
  You can use the xAI Responses API with the `xai.responses(modelId)` factory method for server-side agentic tool calling. This enables the model to autonomously orchestrate tool calls and research on xAI's servers.
150
150
 
151
151
  ```ts
152
- const model = xai.responses('grok-4.20-non-reasoning');
152
+ const model = xai.responses('grok-4.5');
153
153
  ```
154
154
 
155
155
  The Responses API provides server-side tools that the model can autonomously execute during its reasoning process:
@@ -171,7 +171,7 @@ import { xai } from '@ai-sdk/xai';
171
171
  import { generateText } from 'ai';
172
172
 
173
173
  const { text } = await generateText({
174
- model: xai.responses('grok-3'),
174
+ model: xai.responses('grok-4.5'),
175
175
  messages: [
176
176
  {
177
177
  role: 'user',
@@ -192,7 +192,7 @@ import { xai } from '@ai-sdk/xai';
192
192
  import { generateText } from 'ai';
193
193
 
194
194
  const { text } = await generateText({
195
- model: xai('grok-4.3'),
195
+ model: xai('grok-4.5'),
196
196
  messages: [
197
197
  {
198
198
  role: 'user',
@@ -822,6 +822,7 @@ console.log('Sources:', await result.sources);
822
822
 
823
823
  | Model | Image Input | Object Generation | Tool Usage | Tool Streaming | Reasoning |
824
824
  | ----------------------------- | ------------------- | ------------------- | ------------------- | ------------------- | ------------------- |
825
+ | `grok-4.5` | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> |
825
826
  | `grok-4.20-reasoning` | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> |
826
827
  | `grok-4.20-non-reasoning` | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Cross size={18} /> |
827
828
  | `grok-4-1-fast-reasoning` | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> | <Check size={18} /> |
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ai-sdk/xai",
3
- "version": "3.0.105",
3
+ "version": "3.0.107",
4
4
  "license": "Apache-2.0",
5
5
  "sideEffects": false,
6
6
  "main": "./dist/index.js",
@@ -29,9 +29,9 @@
29
29
  }
30
30
  },
31
31
  "dependencies": {
32
- "@ai-sdk/openai-compatible": "2.0.58",
33
- "@ai-sdk/provider-utils": "4.0.37",
34
- "@ai-sdk/provider": "3.0.13"
32
+ "@ai-sdk/openai-compatible": "2.0.60",
33
+ "@ai-sdk/provider": "3.0.14",
34
+ "@ai-sdk/provider-utils": "4.0.39"
35
35
  },
36
36
  "devDependencies": {
37
37
  "@types/node": "20.17.24",
@@ -1,6 +1,7 @@
1
1
  import { z } from 'zod/v4';
2
2
 
3
3
  export type XaiResponsesModelId =
4
+ | 'grok-4.5'
4
5
  | 'grok-4.3'
5
6
  | 'grok-4.20-0309-reasoning'
6
7
  | 'grok-4.20-0309-non-reasoning'
@@ -2,6 +2,7 @@ import { z } from 'zod/v4';
2
2
 
3
3
  // https://docs.x.ai/docs/models
4
4
  export type XaiChatModelId =
5
+ | 'grok-4.5'
5
6
  | 'grok-4.3'
6
7
  | 'grok-4.20-0309-reasoning'
7
8
  | 'grok-4.20-0309-non-reasoning'
@@ -62,6 +62,14 @@ function resolveStartImage(
62
62
  return getFirstFrameImage(options) ?? options.image;
63
63
  }
64
64
 
65
+ function getTopLevelMediaType(mediaType: string): string {
66
+ const slashIndex = mediaType.indexOf('/');
67
+ return slashIndex === -1 ? mediaType : mediaType.substring(0, slashIndex);
68
+ }
69
+
70
+ const isVideoFile = (file: Experimental_VideoModelV3File): boolean =>
71
+ file.mediaType != null && getTopLevelMediaType(file.mediaType) === 'video';
72
+
65
73
  function fileToXaiImageUrl(file: Experimental_VideoModelV3File): string {
66
74
  if (file.type === 'url') {
67
75
  return file.url;
@@ -71,17 +79,35 @@ function fileToXaiImageUrl(file: Experimental_VideoModelV3File): string {
71
79
  typeof file.data === 'string'
72
80
  ? file.data
73
81
  : convertUint8ArrayToBase64(file.data);
74
- return `data:${file.mediaType ?? 'image/png'};base64,${base64Data}`;
82
+ return `data:${file.mediaType};base64,${base64Data}`;
75
83
  }
76
84
 
77
85
  // Resolves the reference images for R2V generation. First-class
78
86
  // `inputReferences` win over the legacy `referenceImageUrls` provider option.
87
+ // Video references are not supported for reference-to-video and are skipped
88
+ // with a warning.
79
89
  function resolveReferenceImages(
80
90
  options: XaiVideoDoGenerateOptions,
81
91
  xaiOptions: XaiParsedVideoModelOptions | undefined,
92
+ warnings: SharedV3Warning[],
82
93
  ): Array<{ url: string }> | undefined {
83
94
  if (options.inputReferences != null && options.inputReferences.length > 0) {
84
- return options.inputReferences.map(reference => ({
95
+ const imageReferences = options.inputReferences.filter(reference => {
96
+ if (isVideoFile(reference)) {
97
+ warnings.push({
98
+ type: 'unsupported',
99
+ feature: 'inputReferences',
100
+ details:
101
+ 'xAI reference-to-video accepts image references only. The video ' +
102
+ 'reference was ignored. Use providerOptions.xai.mode ' +
103
+ '"extend-video" to continue from a video.',
104
+ });
105
+ return false;
106
+ }
107
+ return true;
108
+ });
109
+
110
+ return imageReferences.map(reference => ({
85
111
  url: fileToXaiImageUrl(reference),
86
112
  }));
87
113
  }
@@ -278,24 +304,44 @@ export class XaiVideoModel implements Experimental_VideoModelV3 {
278
304
  // nested xAI request image object.
279
305
  const startImage = resolveStartImage(options);
280
306
  if (startImage != null) {
281
- body.image = { url: fileToXaiImageUrl(startImage) };
307
+ if (isVideoFile(startImage)) {
308
+ const fromFrameImages = getFirstFrameImage(options) != null;
309
+ warnings.push({
310
+ type: 'unsupported',
311
+ feature: fromFrameImages ? 'frameImages' : 'image',
312
+ details:
313
+ 'xAI does not accept a video as a start/frame image. The video ' +
314
+ 'was ignored. Use providerOptions.xai.mode "extend-video" to ' +
315
+ 'continue from a video instead.',
316
+ });
317
+ } else {
318
+ body.image = { url: fileToXaiImageUrl(startImage) };
319
+ }
282
320
  }
283
321
 
284
322
  // xAI has no first-last-frame interpolation; warn and ignore last_frame.
285
- if (getLastFrameImage(options) != null) {
323
+ const lastFrameImage = getLastFrameImage(options);
324
+ if (lastFrameImage != null) {
286
325
  warnings.push({
287
326
  type: 'unsupported',
288
327
  feature: 'frameImages',
289
- details:
290
- 'xAI video models do not support last_frame. Use ' +
291
- 'providerOptions.xai.mode "extend-video" to continue from a ' +
292
- "video's last frame. The last frame image was ignored.",
328
+ details: isVideoFile(lastFrameImage)
329
+ ? 'xAI does not accept a video as a start/frame image. The video ' +
330
+ 'last frame was ignored. Use providerOptions.xai.mode ' +
331
+ '"extend-video" to continue from a video instead.'
332
+ : 'xAI video models do not support last_frame. Use ' +
333
+ 'providerOptions.xai.mode "extend-video" to continue from a ' +
334
+ "video's last frame. The last frame image was ignored.",
293
335
  });
294
336
  }
295
337
 
296
338
  // Reference images for R2V (reference-to-video) generation
297
339
  if (hasReferenceImages) {
298
- const referenceImages = resolveReferenceImages(options, xaiOptions);
340
+ const referenceImages = resolveReferenceImages(
341
+ options,
342
+ xaiOptions,
343
+ warnings,
344
+ );
299
345
  if (referenceImages != null) {
300
346
  body.reference_images = referenceImages;
301
347
  }