The engineering bottleneck with assembled stacks
Integration engineers process webhooks inside the request handler because that is how the first endpoint is written, then run into the provider’s retry behaviour: the endpoint times out during a deploy, the provider retries for two days, and the same payment event is processed three times while another is never seen. The failure record lives in the provider’s dashboard, expiring, unqueryable, and always somebody else’s screenshot.
Architecture on the Software Lifecycle Cloud
The receiving function does three things only: verify the signature, persist the payload under the provider’s event id, respond. Processing workers claim unprocessed rows, do the real work, and mark outcomes — processed, failed with the error, or dead-lettered after the attempt budget. Because the raw body is stored, reprocessing after a bug fix replays the true payload, not a reconstruction.
Idempotency is a key, not a hope
Providers deliver at least once; your table design should assume it. With the provider’s event id as the key, a redelivery lands on the same row and the processor can see it has already succeeded. “Have we handled Stripe event X?” becomes a keyed read with a timestamp and an outcome, which is the entire conversation in the incident channel, settled in one line.
- Raw payloads are stored before processing, so a processor bug is replayable rather than fatal
- Dead letters are rows with errors attached — visible, countable, retryable from data
- Signature secrets are project secrets; rotation is a declaration, not a scavenger hunt
The deploy-window dividend
Because receiving and processing are separate, deploys stop being webhook weather: the receiver’s surface is tiny and stable, and processors can pause during their own deploy while rows accumulate safely. Providers see fast acknowledgements throughout — the behaviour that keeps you off their degraded-endpoint lists.
Frequently asked questions
As fast as a signature check and one table write — milliseconds. All slow work happens in workers claiming rows afterwards, so provider timeouts stop correlating with your processing complexity.
The row accumulates attempts with their errors and lands in a dead-letter state you define. It stays queryable forever (or until your retention sweep), and a fixed processor can be pointed at the dead-letter set explicitly.
Yes — the stored raw bodies are the replay source. Select the window or the provider and re-run processing; idempotency keys ensure events already applied do not apply twice.
Related capabilities, architectures, and comparisons
Ship your stack on the Software Lifecycle Cloud.
Closed preview on dedicated European infrastructure. Bring a repository or start from a blueprint.