Stripe Webhooks vs Success Page Redirects
By Shawn Michael Thomas II, Founder of Simple Easy Transactions · Published ·
Is a redirect to my success page proof that a Stripe payment went through? No. A redirect only tells me where the customer's browser went, not what Stripe decided. The customer can close the tab, lose signal or open the success page directly, and some payment methods settle later. A signed Stripe webhook comes from Stripe's servers to mine, carries a signature I check, and is retried until I confirm it. I deliver from that, and I record it so a repeat can't deliver twice.
AT A GLANCE
Signed webhook vs Browser redirect.
| Question | Signed webhook | Browser redirect |
|---|---|---|
| Who sends it | Stripe's servers, directly to yours | The customer's browser, following a redirect |
| Can it be skipped | No; Stripe retries until you confirm it | Yes; closing the tab skips it |
| Can it be faked | Not without your signing secret | Yes; anyone can open the success page |
| When it arrives | When Stripe reaches a final answer | When the browser moves, which can be earlier |
| Safe to deliver the order from | Yes, once checked and recorded | No; treat it as a courtesy message |
| Right place to thank the customer | No; the customer never sees it | Yes |
HOW EACH ONE WORKS
How each one works.
Stripe signs each webhook with your endpoint's signing secret and sends the signature in the Stripe-Signature header. Check it against the raw request body, before anything parses or reformats it, and reject deliveries whose timestamp is too old. Stripe's libraries default to a five-minute window, which stops a captured request from being replayed later.
In live mode, Stripe retries a delivery that doesn't get a success response for up to three days, and the same event can arrive more than once or out of order. Store each event you've processed, make your handler safe to run twice, and respond quickly: do slow work after responding, because a timeout counts as a failure and triggers another retry.
The success page still has a job. It's the right place to thank the customer and explain what happens next, as long as nothing that matters, such as access, shipping or an invoice, depends on it.
FIELD NOTES
What I've learned building this.
- Every order on this site is recorded from a signed Stripe event, in a ledger that collapses a retried or duplicated event into one record. The thank-you page never records anything.
- My thank-you page says plainly that opening it doesn't confirm a payment, so nobody mistakes it for a receipt.
- The Embedded Checkout Starter Kit checks the webhook signature on the raw body before it parses anything, because a framework that parses the body first makes every signature fail.
HOW TO CHOOSE
How I'd choose.
- Use the success page for what the customer sees: a thank-you and the next steps.
- Use the signed webhook for anything that matters: delivery, access, invoicing or crediting an account.
- Record every processed event under a lasting key, because Stripe retries, and a retry must never produce a second outcome.
SOURCES
Where these facts come from.
Sources checked on . Providers change their products and rules, so the linked pages are the final word.