
Stripe checkout sessions—the payment links you generate via the API or dashboard—expire. By default, a session lives for 24 hours. After that, the link returns an error, and your customer sees a blank page or an “expired” message depending on how you built the flow.
If you’re selling one-time products, launching a course, or running a time-limited offer, session expiration matters. A customer who bookmarks your payment link on Monday may find it dead by Wednesday. Here’s how the mechanism works, how to control it, and when you should shorten or extend the window.
How Stripe checkout session expiration works
When you create a checkout session via the Stripe API, you can set an expires_at parameter. This is a Unix timestamp. If you don’t set it, Stripe defaults to 24 hours from session creation (Stripe API reference, checked November 2026).
The maximum allowed expiration is 24 hours. You cannot extend a session beyond that window without creating a new session. The minimum is effectively immediate—you can set expiration as soon as the session is created, though there’s no practical reason to do so.
Once a session expires, the URL still resolves, but Stripe shows an error. If you’ve built a custom success or cancel flow, the customer may land on a generic Stripe page instead of your site.
When to shorten the expiration window
Flash sales, early-bird pricing, and limited-inventory drops benefit from shorter session lifetimes. If your offer ends at midnight, set expires_at to match that deadline. This prevents customers from bookmarking a checkout link with old pricing and completing payment after the window closes.
Example: you’re selling 50 seats to a workshop. You open registration at 9:00 AM and close at 5:00 PM the same day. Set session expiration to 5:00 PM. Any link generated during the day dies at the cutoff, and you avoid the edge case where someone checks out at 6:00 PM with a stale session.
Shorter expiration also reduces the risk of price or inventory desync. If you update a product price or mark it out of stock, existing sessions may still reference the old state until they expire or you manually invalidate them.
The trade-off: customer friction
Short expiration windows introduce friction. A customer who adds your link to a tab and returns three hours later may find it dead. They’ll need to start over—navigate back to your site, click through to checkout again, and re-enter payment details if autofill doesn’t catch them.
For evergreen products or recurring subscriptions, the default 24-hour window usually works. Customers rarely sit on a payment link for more than a few hours, and the risk of stale pricing is low if your product catalog is stable.
If you’re running a high-touch sales process—say, sending a custom quote via email—consider the 24-hour limit carefully. A prospect who receives your link Monday afternoon may not review it until Tuesday evening. If the session expires, they’ll email you for a new link, and you’ve added a round-trip to the sales cycle.
One non-obvious detail: session expiration and webhooks
Stripe does not fire a checkout.session.expired event by default. If you’re tracking session state in your own database, you’ll need to poll or handle expiration client-side. Stripe’s dashboard shows session status, but you won’t get a webhook notification when a session times out unless you’ve built custom logic to listen for the absence of a checkout.session.completed event within your expected window.
This matters if you’re pre-reserving inventory or seats. If you decrement stock when a session is created and rely on expiration to release it, you’ll need a background job that checks session age and restores inventory for sessions that expired without completion. Stripe won’t do that for you.
If you’re using Stripe for one-time payments, course sales, or limited-run products, audit your session expiration settings. The default 24 hours is reasonable for most cases, but it’s not universal. Shortening expiration tightens control over pricing and inventory; extending it—within the 24-hour cap—reduces friction for slower-moving prospects.
Set expiration deliberately. Don’t leave it to default and assume it matches your offer’s lifecycle.
Have a question about payment flows or checkout quirks? Reply to this email—we read every one and fold operator questions into future issues.
