Skip to main content
Webhooks are in beta. Event types and payload shapes may still change. We’ll email orgs with active endpoints before any breaking change.
When a subscribed event happens, Origami POSTs a signed JSON envelope to a URL you configure in Settings → Developers → Webhooks, or via POST /api/v3/account/webhooks.

API Jobs events

v3-only. These fire when a Job changes status — searches, fetches, enrichment, campaign drafts, domain purchases, mailbox provisioning, and chat messages. Subscribe to specific types or the job.* wildcard. Payloads echo the metadata you passed when admitting the Job, so you can correlate without polling. data.sequence is a monotonic generation — ignore any event whose sequence is not greater than the last one you processed for that job_id.

Tables events

Subscribe to table.run.completed, the table.* wildcard, or * (everything). Missed delivery on a v3 upsert? Recover with GET /api/v3/jobs/{job_id} using the embedded enrichment Job id. On v2, recover with GET /api/v2/tables/{tableId}/runs/{runId} using the run_id from the payload (or enrichment_run.tableRunId from the upsert response).

Sequencer events

Every sequencer payload carries campaign_id (nullable) — the join key for routing a touch back to the campaign that produced it — and sender.id, the stable sender id from GET /api/v3/account/senders. Subscribe to specific event types, the sequence.* wildcard, the sequence.connection.* sub-wildcard, table.*, job.*, or * (everything, including future event types).

Delivery guarantees

  • At-least-once delivery. A single event can produce more than one POST under partial failure. Receivers must dedupe on the webhook-id header.
  • Up to 10 attempts following the Standard Webhooks spec retry table — initial + 9 retries with ±15% jitter spanning roughly 75 hours.
  • 410 Gone auto-disables the endpoint per the spec. Re-enable manually from the dashboard.
  • webhook-id is stable across retries. webhook-timestamp is recomputed per attempt — use it for replay protection (±5 min).

Signing

Every request carries three headers: Signed string is {webhook-id}.{webhook-timestamp}.{raw-body}, keyed by the base64-decoded bytes of your whsec_… secret (after stripping the whsec_ prefix). This is the canonical Standard Webhooks scheme — verify with Svix’s standardwebhooks SDK or the copy-paste snippets in signature verification (Node, Python, Go, Ruby, Rust, curl + openssl).

Next steps