Skip to main content
Lip-sync needs a project with a finished dub and a video that shows faces. You need the scopes lipsync:write and credits:spend. A paid run is priced on the whole video, even when the plan processes only part of it. Pricing gives the formula.

1. Estimate

Besides eligible and total_minutes, details has the multiplier, the processed_seconds, whether a face check has already found a face (video_has_face, face_check_required) and the state of any earlier run (previous_run).

2. Start it

The answer is a lipsync job: it charges, runs a face check unless one already ran, waits for a worker and renders. The job’s stage says which (face_check, waiting_for_worker, rendering).

The free run

A project has one free run. It costs 1 minute from the free lip-sync pool (lipsync_free_minutes in the balance) and processes the first 60 seconds. It needs no earlier run on the project, and free_trial_run_available in the estimate says whether it is still there. It needs the plan feature lipsync, and lipsync_enhanced for the Enhanced model, but not lipsync_paid.

3. Get the result

current_result.video.url is the video, whichever channel produced it. The same video is the output lipsync_video and, for a run started here, the job’s result.video. When the plan has no lipsync_download, download_restricted is true and the link is withheld. is_trimmed and processed_seconds say when only part was processed: the free run stops at 60 seconds, and the plan’s limits.lipsync_max_seconds can be shorter than the video.

What can go wrong

A job that fails is refunded, whatever ended it: a failure, a timeout or a video with no face. To try again, send a new Idempotency-Key. A later dub makes the result outdated: outdated on the state is true and current_result is null, while the job’s result.video stays readable with is_outdated: true. Then you can lip-sync the new dub.

The whole program

lipsync_video.py