POST to your URL.
The key scope for managing subscriptions is
webhooks:manage. Delivery is
at-least-once: retries are possible, so deduplicate on the id field.Subscribe
secret — shown once. Store it: it verifies
the signature of every delivery.
Thin payload
An event carries the type, the resource id, and the time — but not the data itself:GET /developer/v1/employees/{employee_id}. That way the key’s scope and field
redaction apply automatically, and personal data never leaves for an external URL.
Event types
A person rename arrives as
employee.changed for each affected employee — this is
the primary channel to keep names fresh (the updated_since filter on lists does not
reflect such changes).
Document events — document.sent, document.completed, document.rejected, and
others — have their own guide: Document events.
employee.changed covers both creation and change: on receiving it, re-read the
resource and upsert. There is deliberately no separate created event — the source
cannot always reliably tell a first appearance from a later change.Verifying the signature
Every delivery carries a header:v1 is HMAC-SHA256(secret, "{t}.{request body}") in hex. Verify it on your
side and reject the request if the signature does not match or t is older than five
minutes (replay protection).
Delivery and reliability
- Respond
2xxquickly and process asynchronously. The timeout is 10 seconds. - On failure, the event is redelivered — up to 8 attempts with exponentially growing backoff, roughly a day in total.
- After 20 consecutive permanently failed deliveries the endpoint is disabled automatically and no new events are sent to it.
- Delivery is at-least-once: retries are possible. Use the event
idto deduplicate.
Operations
- Re-enabling. A disabled endpoint (after a run of failures, or manually) is re-enabled in the app settings: Integrations → Webhooks. There is currently no re-enable endpoint in the Developer API.
- Events during downtime are not replayed. While an endpoint is disabled,
events do not queue up. After re-enabling, reconcile by polling:
GET /employees?updated_since=<disabled-at time>. - Secret rotation. The secret is issued once at creation and is not rotated. To replace it, create a new endpoint with the same URL and event types, switch your signature check to the new secret, then delete the old endpoint.