SpyBara
Go Premium

Documentation 2026-09-25 23:01 UTC to 2026-09-26 23:59 UTC

4 files changed +31 −82. View all changes and history on the product overview
2026
Wed 30 23:57 Tue 29 23:59 Mon 28 23:57 Sun 27 22:59 Sat 26 23:59 Fri 25 23:01 Thu 24 23:59 Wed 23 23:59 Tue 22 23:58 Mon 21 23:00 Sun 20 23:01 Sat 19 23:59 Fri 18 23:59 Thu 17 10:04 Wed 16 19:01 Tue 15 17:00 Mon 14 06:00 Sun 13 05:00 Fri 11 21:00 Tue 8 21:00 Mon 7 22:57 Thu 3 16:59 Wed 2 22:03
Details

269 269 

270`prompt` is optional in every first & last frame request. Include one to steer motion and camera work between the frames; omit it to let the frames alone drive the clip.270`prompt` is optional in every first & last frame request. Include one to steer motion and camera work between the frames; omit it to let the frames alone drive the clip.

271 271 

272`last_frame` uses the same URL, data-URI, and `file_id` shapes as [image-to-video](/developers/model-capabilities/video/image-to-video). The Python SDK and Vercel AI SDK do not yet expose a dedicated `last_frame` parameter; send it on the REST body.272`last_frame` uses the same URL, data-URI, and `file_id` shapes as [image-to-video](/developers/model-capabilities/video/image-to-video). In the xAI Python SDK, pass `last_frame_url` (or `last_frame_file_id` for a Files API upload) alongside `image_url` (or `image_file_id`). The Vercel AI SDK does not expose `last_frame` yet; send it on the REST body.

273 273 

274Classic `grok-imagine-video` rejects `last_frame` and rejects combining `image` with reference inputs.274Classic `grok-imagine-video` rejects `last_frame` and rejects combining `image` with reference inputs.

275 275 

276```python customLanguage="pythonXAI"

277import os

278import xai_sdk

279 

280client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))

281 

282response = client.video.generate(

283 prompt="The camera dollies from the sunlit doorway to the window, settling on the closing frame.",

284 model="grok-imagine-video-1.5",

285 image_url="<FIRST_FRAME_URL>",

286 last_frame_url="<LAST_FRAME_URL>",

287 duration=8,

288 aspect_ratio="16:9",

289 resolution="720p",

290)

291 

292print(response.url)

293```

294 

276```python customLanguage="pythonRequests"295```python customLanguage="pythonRequests"

277import os296import os

278import time297import time


363| Spacing | Anchors snap to a 1/3-second grid. Two keyframes that round to the same slot are rejected, so keep them at least 1/3 s apart. |382| Spacing | Anchors snap to a 1/3-second grid. Two keyframes that round to the same slot are rejected, so keep them at least 1/3 s apart. |

364| Inputs | Each `image` accepts the same URL, data-URI, and `file_id` shapes as [image-to-video](/developers/model-capabilities/video/image-to-video). |383| Inputs | Each `image` accepts the same URL, data-URI, and `file_id` shapes as [image-to-video](/developers/model-capabilities/video/image-to-video). |

365 384 

366The Python SDK and Vercel AI SDK do not yet expose a dedicated `keyframes` parameter; send it on the REST body. Classic `grok-imagine-video` rejects `keyframes`, and keyframes cannot be combined with video editing.385In the xAI Python SDK, `keyframes` is a list of dicts that flatten the REST `image` object: each entry takes `image_url` (or `image_file_id`) and `timestamp`, the REST `timestamp_s` in seconds, as in `{"image_url": "<KEYFRAME_URL_1>", "timestamp": 2.0}`. Pin the endpoints with `image_url` and `last_frame_url`. The Vercel AI SDK does not expose `keyframes` yet; send it on the REST body.

367 

368```python customLanguage="pythonRequests"

369import os

370import time

371import requests

372 386 

373headers = {387Classic `grok-imagine-video` rejects `keyframes`, and keyframes cannot be combined with video editing.

374 "Content-Type": "application/json",

375 "Authorization": f"Bearer {os.environ['XAI_API_KEY']}",

376}

377 

378response = requests.post(

379 "https://api.x.ai/v1/videos/generations",

380 headers=headers,

381 json={

382 "model": "grok-imagine-video-1.5",

383 "prompt": "A slow tracking shot through the workshop: the sketch on the bench becomes a clay model, then the finished bronze in the window.",

384 "image": {"url": "<FIRST_FRAME_URL>"},

385 "keyframes": [

386 {"image": {"url": "<KEYFRAME_URL_1>"}, "timestamp_s": 3.0},

387 {"image": {"url": "<KEYFRAME_URL_2>"}, "timestamp_s": 6.0},

388 ],

389 "last_frame": {"url": "<LAST_FRAME_URL>"},

390 "duration": 8,

391 "aspect_ratio": "16:9",

392 "resolution": "720p",

393 },

394)

395 

396request_id = response.json()["request_id"]

397 388 

398while True:389### Example: a year in one request

399 result = requests.get(

400 f"https://api.x.ai/v1/videos/{request_id}",

401 headers={"Authorization": headers["Authorization"]},

402 )

403 data = result.json()

404 if data["status"] == "done":

405 print(data["video"]["url"])

406 break

407 elif data["status"] == "expired":

408 print("Request expired")

409 break

410 time.sleep(5)

411```

412 390 

413```bash391This request uses every kind of pin at once. A single oak is pinned as winter in the first frame, spring and summer as keyframes at 3 and 6 seconds, and autumn as the last frame at 9 seconds; the model animates the seasons in between. Select a pin to see the exact frame the video passes through, or press play to watch the whole year.

414REQUEST_ID=$(curl -s -X POST https://api.x.ai/v1/videos/generations \

415 -H "Content-Type: application/json" \

416 -H "Authorization: Bearer $XAI_API_KEY" \

417 -d '{

418 "model": "grok-imagine-video-1.5",

419 "prompt": "A slow tracking shot through the workshop: the sketch on the bench becomes a clay model, then the finished bronze in the window.",

420 "image": {"url": "<FIRST_FRAME_URL>"},

421 "keyframes": [

422 {"image": {"url": "<KEYFRAME_URL_1>"}, "timestamp_s": 3.0},

423 {"image": {"url": "<KEYFRAME_URL_2>"}, "timestamp_s": 6.0}

424 ],

425 "last_frame": {"url": "<LAST_FRAME_URL>"},

426 "duration": 8,

427 "aspect_ratio": "16:9",

428 "resolution": "720p"

429 }' | jq -r '.request_id')

430 392 

431while true; do393Pins work best when they share a scene. The four stills started as one generated winter image, and each season is an [image edit](/developers/model-capabilities/images/editing) of it, so the tree, horizon, and camera angle stay identical and the model only has to animate the change of season.

432 RESULT=$(curl -s https://api.x.ai/v1/videos/$REQUEST_ID \

433 -H "Authorization: Bearer $XAI_API_KEY")

434 STATUS=$(echo "$RESULT" | jq -r '.status')

435 if [ "$STATUS" = "done" ]; then

436 echo "$RESULT" | jq -r '.video.url'

437 break

438 elif [ "$STATUS" = "failed" ] || [ "$STATUS" = "expired" ]; then

439 echo "Request $STATUS"; echo "$RESULT" | jq .

440 break

441 fi

442 sleep 5

443done

444```

445 394 

446## Related395## Related

447 396 

quickstart.md +3 −3

Details

2 2 

3# Quickstart3# Quickstart

4 4 

5Welcome! In this guide, we'll walk you through the basics of using the xAI API, from creating an account to making your first request.5Welcome! In this guide, we'll walk you through the basics of using the SpaceXAI API, from creating an account to making your first request.

6 6 

7## Step 1: Create an xAI account7## Step 1: Create a SpaceXAI account

8 8 

9Sign up for an account at [console.x.ai](https://console.x.ai/login?mode=sign-up\&utm_source=docs\&utm_medium=referral\&utm_campaign=quickstart), then load it with credits to start using the API.9Sign up for an account at [console.x.ai](https://console.x.ai/login?mode=sign-up\&utm_source=docs\&utm_medium=referral\&utm_campaign=quickstart), then load it with credits to start using the API.

10 10 


44 44 

45## Step 4: Make your first request45## Step 4: Make your first request

46 46 

47Send a coding prompt to [Grok Build](/build/overview) (`grok-4.7`) and get a response. The same model powers agentic coding in Grok Build and is available on the API in early access:47Send a coding prompt to [Grok Build](/build/overview) (`grok-4.7`) and get a response. The same model powers agentic coding in Grok Build and is available on the SpaceXAI API:

48 48 

49```bash49```bash

50curl https://api.x.ai/v1/responses \50curl https://api.x.ai/v1/responses \

rate-limits.md +2 −2

Details

41| grok-4.20-0309-non-reasoning | T0: 37, T1: 50, T2: 75, T3: 125, T4: 208 | T0: 10M, T1: 15M, T2: 25M, T3: 45M, T4: 85M |41| grok-4.20-0309-non-reasoning | T0: 37, T1: 50, T2: 75, T3: 125, T4: 208 | T0: 10M, T1: 15M, T2: 25M, T3: 45M, T4: 85M |

42| grok-build-0.1 | T0: 37, T1: 50, T2: 75, T3: 125, T4: 208 | T0: 10M, T1: 15M, T2: 25M, T3: 45M, T4: 85M |42| grok-build-0.1 | T0: 37, T1: 50, T2: 75, T3: 125, T4: 208 | T0: 10M, T1: 15M, T2: 25M, T3: 45M, T4: 85M |

43| grok-4.20-multi-agent-0309 | T0: 9, T1: 12, T2: 18, T3: 31, T4: 56 | T0: 2.5M, T1: 3.7M, T2: 6.2M, T3: 11M, T4: 21M |43| grok-4.20-multi-agent-0309 | T0: 9, T1: 12, T2: 18, T3: 31, T4: 56 | T0: 2.5M, T1: 3.7M, T2: 6.2M, T3: 11M, T4: 21M |

44| grok-imagine-image | T0: 6, T1: 12, T2: 25, T3: 50, T4: 100 | — |

45| grok-imagine-image-2.0 | T0: 6, T1: 12, T2: 25, T3: 50, T4: 100 | — |44| grok-imagine-image-2.0 | T0: 6, T1: 12, T2: 25, T3: 50, T4: 100 | — |

46| grok-imagine-image-quality | T0: 6, T1: 12, T2: 25, T3: 50, T4: 100 | — |45| grok-imagine-image-quality | T0: 6, T1: 12, T2: 25, T3: 50, T4: 100 | — |

47| grok-imagine-video | T0: 10, T1: 20, T2: 39, T3: 79, T4: 158 | — |46| grok-imagine-image | T0: 6, T1: 12, T2: 25, T3: 50, T4: 100 | — |

48| grok-imagine-video-1.5 | T0: 10, T1: 20, T2: 39, T3: 79, T4: 158 | — |47| grok-imagine-video-1.5 | T0: 10, T1: 20, T2: 39, T3: 79, T4: 158 | — |

48| grok-imagine-video | T0: 10, T1: 20, T2: 39, T3: 79, T4: 158 | — |

49 49 

50**Voice & Audio**50**Voice & Audio**

51 51 

Details

54 54 

55 * `summary` (string | null) — A summary of the model's reasoning process. Possible values are \`auto\`, \`concise\` and \`detailed\`. Only included for compatibility. The model shall always return \`detailed\`.55 * `summary` (string | null) — A summary of the model's reasoning process. Possible values are \`auto\`, \`concise\` and \`detailed\`. Only included for compatibility. The model shall always return \`detailed\`.

56 56 

57* `reasoning_effort` (string | null) — reasoning\_effort alternative to reasoning configuration. This is a non-standard field meant to ease user experience. We only look at this if the reasoning field is unset.57* `reasoning_effort` (string | null) — Non-standard alternative to \`reasoning.effort\` that accepts the same values. We only look at this if the reasoning field is unset.

58 58 

59* `safety_identifier` (string | null) — Supplied by the API client to identify the end user behind this request. A stable string that uniquely identifies each of your users; hash your internal user id or username rather than sending an email or name. Stored with the request metadata so a usage-policy violation can be attributed to that user rather than to the API key.59* `safety_identifier` (string | null) — Supplied by the API client to identify the end user behind this request. A stable string that uniquely identifies each of your users; hash your internal user id or username rather than sending an email or name. Stored with the request metadata so a usage-policy violation can be attributed to that user rather than to the API key.

60 60