Video generation

Grok Imagine

xAI's video models. Start a generation, poll it, download the video.

Video takes longer than an HTTP request should stay open, so generation is a job: POST /v1/videos/generations starts it and answers at once with a request_id, and GET /v1/videos/{request_id} reports its progress until the video is ready.

Model id
grok-imagine-1xAI’s grok-imagine-video: up to 720p
grok-imagine-1.5xAI’s grok-imagine-video-1.5: native 1080p; reference images, keyframes and a fixed last frame

Both make 1 to 15 seconds of video with audio, from text or from a starting image.

Start a generation

curl https://platform.parseclab.ai/v1/videos/generations \
  -H "Authorization: Bearer $PARSEC_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"model": "grok-imagine-1.5", "prompt": "An otter surfing at sunset", "duration": 6}'
{"request_id": "vid_eyJvIjoiYWNjdF8..."}

The body is xAI’s, passed through with the model id swapped:

Field
modelgrok-imagine-1 or grok-imagine-1.5. Required.
promptWhat to generate. Required unless an image is given.
durationSeconds, 1 to 15. Default 8.
aspect_ratio16:9 (default), 9:16, 1:1, 4:3, 3:4, 3:2, 2:3, 21:9 or 5:2. Ignored for image-to-video, which keeps the image’s shape.
resolution480p (default), 720p or 1080p.
imageA starting frame, for image-to-video.
generate_audiofalse for a silent video.

grok-imagine-1.5 also takes reference_images, reference_audios, last_frame and keyframes. See xAI’s video docs for these fields’ exact shapes.

Poll until it is done

curl https://platform.parseclab.ai/v1/videos/$REQUEST_ID \
  -H "Authorization: Bearer $PARSEC_API_KEY"

While the video renders:

{"status": "pending"}

When it is ready:

{
  "status": "done",
  "video": {"url": "https://vidgen.x.ai/.../video.mp4", "duration": 6, "respect_moderation": true},
  "model": "grok-imagine-video-1.5"
}

If it fails, the answer is still 200, with "status": "failed" and error.code set to one of invalid_argument, permission_denied, failed_precondition, service_unavailable or internal_error.

Poll every few seconds. Most videos take somewhere from tens of seconds to a few minutes.

Download the video. The url is xAI’s and expires; Parsec does not keep a copy.

Python

import os, time, requests

base = "https://platform.parseclab.ai/v1"
headers = {"Authorization": f"Bearer {os.environ['PARSEC_API_KEY']}"}

job = requests.post(f"{base}/videos/generations", headers=headers, json={
    "model": "grok-imagine-1.5",
    "prompt": "An otter surfing at sunset",
    "duration": 6,
}).json()

while True:
    r = requests.get(f"{base}/videos/{job['request_id']}", headers=headers).json()
    if r["status"] != "pending":
        break
    time.sleep(5)

if r["status"] == "done":
    open("otter.mp4", "wb").write(requests.get(r["video"]["url"]).content)
else:
    print(r["error"])

Usage and limits

  • Billing is per second of generated video, at the prices on the models page, whatever the resolution. You are charged once, when a poll first finds the video done; polling it again is free, and failed generations cost nothing.
  • Starting a generation needs credit; an empty balance is refused with 402.
  • A request_id works only with keys of the account that started the job; any other key gets 404.
  • Editing and extending videos (/v1/videos/edits, /v1/videos/extensions) are not supported yet.