GuidesRecipesAPI ReferenceChangelog
Log In
Guides

Webhook Delivery & Retry Behavior

Snappt sends outbound webhooks to URLs you configure via POST /webhooks. This document describes how those requests are made, what counts as a successful delivery, and how retries work so you can build a robust receiver.

Request Shape

Every webhook is an HTTP request issued by Snappt to the URL you registered:

  • Content-Type: application/json.
  • Body: compact JSON (no whitespace). The exact bytes are what the signature is computed over.
  • Headers: Snappt-Signature-v2 plus any custom headers you registered on the webhook.
  • Timeout: 30 seconds. If your endpoint has not sent response headers within 30 seconds, the request is aborted and treated as a failure.

Your endpoint should respond quickly, as soon as you've verified you have a matching applicant. Long-running work (database writes, downstream API calls, report fetching) should happen after you have returned a 2xx response, not before.

What Counts as a Successful Delivery

A delivery is considered successful when your endpoint returns an HTTP 200 Status Code within the 30-second timeout.

Any of the following are treated as a failure and recorded as such:

  • Non-2xx status codes (3xx, 4xx, 5xx — including 301/302 redirects, which are not followed).
  • Connection errors (DNS failure, connection refused, TLS handshake failure, etc.).
  • Timeouts (no response within 30s).

Retry Behavior

Retry behavior depends on the event type.

Event typeRetried?Retry window
REPORT_READYYesUp to 24 hours after the report completed
APPLICATION_SUBMITTEDNoSingle delivery attempt only
IDV_PRE_TOURNoSingle delivery attempt only

REPORT_READY retries

REPORT_READY events are retried every ~61–70 minutes for 24 hours (~20–24 attempts) . After that, no further attempts are made — even if every prior attempt failed. Redelivery stops as soon as your API returns an HTTP status 200 .

Network errors and timeouts are treated the same as non-2xx responses — they remain eligible for redelivery until the 24-hour window closes.


Designing an Idempotent Receiver

Because failed deliveries are retried and network conditions can cause a successful response to be lost in transit, your endpoint may receive the same event more than once. To handle this safely:

  • Use the data.id (entry/applicant ID) plus eventType as an idempotency key.
  • Treat duplicate deliveries as no-ops and still return 200 OK.
  • Do not rely on receiving an event exactly once.

Operational Notes

  • Order is not guaranteed. Events for different applicants are delivered in parallel; even for the same applicant, a retry of an older event can arrive after a newer event.
  • Inactive webhooks are skipped. If a webhook is marked inactive (isActive = false) via our REST API, no further deliveries or redeliveries occur for it.
  • Per-event subscriptions. A webhook only receives events whose type appears in its events array.