Answer quickly
- Answer with any
2xxstatus within 10 seconds. Anything else counts as a failure: a3xx(Darwin does not follow redirects), a4xx, a5xx, a timeout or a refused connection. - Answer first and do slow work (CRM calls, Slack posts) afterwards in a queue. A receiver that waits on another service is the most common cause of timeouts.
- Darwin reads at most the first 64 KB of your answer and keeps the first 500 characters in the delivery log. Don’t return anything secret.
Handle duplicates and order
- At least once. Darwin may deliver the same event more than once, for example when your server handled it but the answer was lost.
webhook-id(the eventid) is the same on every retry and redelivery. Record the ids you’ve processed and skip repeats. - No ordering. Events can arrive out of order, especially after retries. A
meeting.rescheduledcan arrive before itsmeeting.booked. Usecreated_at, or the object’supdated_at, to decide which is newer, or read the current object from the API.
Retries
If a delivery fails, Darwin tries again after:
That is nine attempts over about three days. After the last one the delivery is marked Failed. You can still send it again by hand for 30 days.
Endpoints that keep failing are switched off
If an endpoint has failures and not one successful delivery for three days, and is still failing, Darwin switches it off and shows why under its address in Integrations → API: Deliveries have failed for three days without one success. Fix the receiver, then switch the endpoint back on. An endpoint that answers410 Gone is switched off at once: that is how a receiver (Zapier, for one) says the subscription is over. Its badge turns from Failing to Off, and GET /webhook_endpoints/{id} shows "status": "disabled" with a disabled_reason.
While an endpoint is off, Darwin does not queue new events for it. To recover:
- Fix your receiver and check it with Send test event.
- Open the endpoint’s ⋯ menu and select Switch on (or
PATCHit with{"status": "enabled"}). Deliveries that were still retrying continue. - Send the events you missed: use Send again in Deliveries, or read
GET /eventsfor the gap and redeliver them.
Check deliveries and send again
Open the endpoint’s ⋯ menu and select Deliveries. Each row shows the event type, whether it was Delivered, is Retrying or Failed, the number of attempts, your server’s last HTTP status or error, and the next try. Send again puts that delivery back in the queue; it goes out within a few seconds. The endpoint row also summarises this week: how many were delivered, failed and are retrying. With the API:queued. Only enabled endpoints subscribed to the event’s type receive it.
Catch up with the event log
Every event from the last 30 days is inGET /events (scope events:read), newest first. It is the pull twin of webhooks: use it after downtime, or instead of webhooks if you would rather poll.
Troubleshooting
Every delivery fails with a signature error on my side
Every delivery fails with a signature error on my side
Check that you verify the raw body, not parsed and re-serialised JSON, and that you base64-decode the secret after removing
whsec_. Frameworks that parse JSON automatically need a raw-body route, like express.raw in Verify signatures.Redirects are not followed
Redirects are not followed
Your URL answered with a
3xx. Use the final address, including https:// and the exact path, often with or without a trailing slash.No answer within 10 seconds
No answer within 10 seconds
Answer
200 before doing the work. Check that your server is reachable from the public internet and not behind a login or firewall.I don't get events for my test chats
I don't get events for my test chats
Preview chats in Darwin never send events. Use Send test event, or have someone use the chat on your live website.