create generation
Create a lip sync generation with application/json — provide each input by url or by assetId from an uploaded asset. For reusable or large local files, upload them first with POST /v2/assets/upload and pass the returned assetId; see Asset Uploads. Use the multipart “Create Generation with Files” form only when uploading direct audio, video, or image file fields; it has a 5 GiB per-file application parser limit, subject to your plan and any lower proxy limits. Nested fields such as input, options, segments, outputAudio, dubParams, and dialogueEdit must be JSON strings in multipart requests. If a text input requires speech synthesis and the ElevenLabs provider is temporarily unavailable, the request returns errorCode elevenlabs_service_unavailable: 504 for provider timeouts and 503 for other provider outages for unkeyed requests. Keyed uncertain outcomes return 503 IDEMPOTENCY_OUTCOME_UNKNOWN instead. An older dialogueEdit preview without segment lipsync and section expansion returns dialogue_edit_retime_required (422). Create a new preview from the same transcript and edits. A dialogueEdit that removes more speech than the surrounding footage can absorb returns errorCode dialogue_edit_removal_too_large (422). When the failing section can be identified, dialogueEditSection on the error names it; change it and create a new preview before submitting again. Retrying the same preview fails again. A video input url that links to a single TikTok, Instagram, Facebook, or YouTube video is imported first: the generation is created PENDING and starts once the video is downloaded, or ends FAILED with errorCode import_failed if the import fails. A linked audio input, or a linked video in a segments or dubbing request, returns 409 import_in_progress until its import finishes; send the same request (with the same Idempotency-Key, if any) again after Retry-After. Link imports can also return 403 import_not_enabled, 422 import_failed, 429 import_daily_limit_reached or concurrency_limit_reached, and 503 import_unavailable. See Asset Uploads. Send the optional Idempotency-Key header on the first request and reuse it with the same payload on retries. An accepted replay returns 200 with the original generation’s current state and Idempotency-Replayed: true. A retry after that generation ended FAILED or REJECTED starts a new generation instead (201). An API-key request without the header that is identical to one your organization sent in the last 60 seconds returns 409 DUPLICATE_SUBMISSION with the original generationId; send a unique Idempotency-Key with each generation you intend. See Idempotent Requests for key validation, conflicts, retention, duplicates, and uncertain-outcome recovery.
Authentification
En-têtes
Case-sensitive organization-scoped key, 1–128 characters matching [A-Za-z0-9._~-]+. Send exactly one header. Reuse the same key and payload for retries of one action; a retry after the generation ended FAILED or REJECTED starts a new one. Use a unique key per intended generation. Retained seven days from acceptance, longer while active or unresolved. Not a JSON field.
Requête
Normal lipsync requests must include exactly one visual input (video or image) and one audio or text input. Dubbed lipsync requests using dubParams must include exactly one video input and no audio or text input, because Sync extracts the dubbing source audio from that video. Image inputs are only supported with the sync-3 model. When using segments, audio or text inputs can carry unique refId values. At most 101 inputs.
Use the id of a completed dialogue edit from POST /v2/dialogue-edits to supply the audio and edited regions. Requires a preview that ran segment lipsync and section expansion (see the job’s segmentLipsyncEnabled and sectionExpansionEnabled). Send exactly one video input, the same video the dialogue edit was made from, and no audio input, segments or dubParams. Billing, status, wait and webhooks work as for any generation. Also accepted in batch rows for organizations with dialogue-edit batches enabled.
Dubbing parameters. When present, audio is extracted from the single video input, dubbed via ElevenLabs into the target language, and then lipsync is run with the dubbed audio. Do not include audio or text inputs with dubParams; requests that send both are rejected.
Optionally attach this generation to a project (created via POST /v2/projects) so it appears in Studio under that project. Must reference a project in your organization — otherwise the request is rejected with 422.
Webhook URL for generation status updates. When the generation reaches a terminal state, Sync sends a POST request with the generation payload and a Sync-Signature header. Verify the header with the organization webhook secret from GET /v2/organizations/webhook/secret. HTTPS is strongly recommended.
Réponse
First acceptance returns 201, as does a keyed retry that starts a new generation after the original ended FAILED or REJECTED. An equivalent keyed replay of an active or completed generation returns 200 with this same response shape and Idempotency-Replayed: true.
Stable, machine-readable error code if the generation failed (e.g. generation_input_video_inaccessible). The full catalog of codes, messages and suggested fixes is served unauthenticated at GET /v2/errors.
Dubbed audio URL. Omitted for generations without dubParams; null until the dubbed track is available.
Reusable AUDIO asset for the dubbed track. Omitted without dubParams; null until available, or when retention settings or a custom output bucket prevent saving an asset.
The URL of the audio synthesized from a text (TTS) input. Only present for generations created with a TTS text input; reuse it as an audio input to keep the same take across generations.
A completion-time estimate captured once when the generation is accepted. Populated only for generations created in sync’s own apps, such as Sync Studio; the field is absent for generations created through the API today. To get an expected finish time for any generation, request it with include=progress and read progress.estimatedFinishAt.
Render progress and expected finish. Only included when the generation is requested with include=progress.

