Skip to main content

Overview

Bulk generation is a loop over your data: one create request per recipient, each with its own values and your own id in metadata, and a webhook (or polling) to collect the results. Every create starts real generation work and, on a managed team, charges credits. Each team can send 30 POST requests per minute (120 for reads) and have 3 downloads of its URLs running at once; over that the API answers 429 with a Retry-After header. Send requests at a steady pace with a small number in flight, wait Retry-After seconds on a 429, and test on a few records first.

Prerequisites

1

A format and its ids

The format endpoint you will call for every row (for example POST /v1/project/create/talking-avatar), and the avatar, voice or media ids it needs from the list endpoints. See Creating videos.
2

Enough credits or your own keys

On a managed team, check the balance covers the batch. On a byok team, make sure the provider keys the format needs are set. See Credits and your own keys.
3

A webhook endpoint

An HTTPS endpoint that records each finished video. See Webhooks.

Basic bulk generation

Step 1: Prepare your data

Fill empty values with defaults before you start, so no script has a gap in it.

Step 2: A simple generator

Store each projectId with the recipient as soon as you get it. The same loop works with any other format: change the endpoint and the body, for example script-to-video with a voiceId and mediaType.

Advanced: concurrency and failures

Run a few requests at once, stop on account-level errors, and never re-send a create whose outcome you do not know.
Requests in unknown may have created a project anyway. Re-send them with the same Idempotency-Key they were first sent with and you get the first answer back instead of a second video. Without a key, re-sending can create and charge a second video: look for them first (by the recipientId in the webhook’s metadata, in your dashboard, or with GET /v1/project/list?source=api, which lists a project as soon as it is created) and only re-send the ones that really did not go through.

Processing CSV files

recipients.csv

Database integration

Keep a row per recipient with its state. This makes the batch resumable and avoids duplicates.
Because a row moves to sending before the request, a crash leaves it in sending rather than pending, so a restart does not send it twice. Review sending and unknown rows by hand.

Webhook management for bulk jobs

Every webhook carries your metadata, so one endpoint can serve the whole batch:
Match on projectId (you stored it when you created the project). Render-failure payloads do not include metadata, so do not rely on it alone.

Catching up

Webhooks are tried 3 times in a row and then dropped. For rows still in created after a while, ask the API directly:

Performance tips

  • Keep a few requests in flight, not hundreds. Each create does real work (validation, pricing, project setup) before it answers, and a team can send 30 POST requests per minute.
  • Test with 3 to 5 rows and watch the videos before sending the full list.
  • Fetch shared data once. Avatar, voice and music lists do not change during a batch.
  • Spread very large batches over time so finished videos keep flowing in while new ones start.

Best practices

Store ids immediately

Save each projectId the moment the create call returns

Use metadata

Put your own recipient id in metadata on every request

Never blind-retry creates

Check before re-sending after a timeout or 5xx

Stop on 401/402

Account errors will fail every remaining request too

Next steps

Personalization

Make each video feel personal

Webhooks

Receive results reliably