Skip to main content
Webhooks let FastDrop push results to your server when jobs complete or fail. If your service can receive an HTTP request, this is the recommended way to integrate — you get the result as soon as it exists and make no status requests at all.
Payload shape changed on 2026-08-15. Endpoints registered before that date keep receiving the old flat payload indefinitely — nothing you have built will break. Endpoints registered since receive the versioned envelope documented below. Check payload_version on GET /v1/webhooks to see which shape an endpoint receives; register a new endpoint to move to the envelope.

Events

batch.progress is off by default because a large batch emits several. Add it to events if you want to track a batch as it runs; it fires at most once per 10% and never for batches under 5 videos. It is never sent at 100% — batch.completed covers that.

Register a webhook

Response
Store the secret now. This is the only response that contains it — GET /v1/webhooks returns just an 8-character prefix. If you lose it, rotate rather than re-registering.
Limits: 5 active endpoints per API key. URLs must use HTTPS.

Webhook payload

Every event arrives in the same envelope:
The event-specific fields are always under data. The four envelope keys are: timestamp reflects the job’s completion time, so events stay correctly ordered even when a batch fan-in dispatches them later.

Headers

X-FastDrop-Event-Id lets you dedupe before parsing the body.

Idempotency

Delivery is at-least-once. A retry, a manual replay, or a network timeout where your server actually succeeded can all produce a repeat. The id is identical every time:
Deduplicate on id, not on job_id — a job legitimately produces more than one event.

Verifying signatures

Every webhook is signed with your secret using HMAC-SHA256. Always verify before acting.
Verify against the raw request body. Re-serialising the parsed JSON will not reproduce our bytes, and the signature will not match. In Express use express.raw(); in FastAPI use await request.body().

A complete receiver

Acknowledge fast and do slow work afterwards. We wait 15 seconds; anything longer counts as a failed delivery and is retried.

Retry policy

Non-2xx or a timeout triggers retries with exponential backoff: After 3 failed attempts the delivery is marked failed. It is not lost — inspect and replay it below.

Delivery history

Every delivery is recorded with the response your server gave.
Response
Filters: webhook_id, job_id, event, status, before, limit. Paginate by passing next_cursor as before. To see exactly what we sent — useful when your parser and our payload disagree — fetch one delivery:
That response adds a payload field containing the verbatim body.

Replaying a delivery

Fixed your endpoint, or lost an event downstream? Replay it:
The payload and its id are unchanged, so a handler that dedupes on id is safe. Replaying costs no credits — you never need to re-run a job to recover an event. A delivery still queued for another automatic attempt returns 409 delivery_in_flight; wait for that attempt to resolve.

Rotating a secret

Returns the endpoint with a new secret, shown once. The old secret stops working immediately — if your handler rejects bad signatures, deploy the new secret before rotating, or expect a few retried deliveries while you catch up.

Testing

Sends a test event in the same shape your endpoint receives for real events, including the signature. If your handler passes this, it will pass a real job.completed.

Per-request webhooks

For a one-off callback without registering an endpoint, pass webhook_url on the submission:
This path is retried and appears in delivery history like any other. Two differences from a registered endpoint:
  • The body is flat — job_id, status, results, completed_at at the top level, no envelope. This shape predates the envelope and is kept for compatibility.
  • It is unsigned unless you pass webhook_secret. Do pass one; without it you cannot prove the request came from us.
Registered endpoints are better for anything long-lived: batch events, a rotatable secret, and the envelope.

Managing endpoints

Getting your results

How webhooks compare to long-poll, and when to use which.