Stripe's Customer Portal Just Got Its Own Pause Button. It Captures Zero Data on Why Anyone Used It.
Stripe shipped native self-serve pausing in the customer portal on Oct 28. It skips your cancellation flow entirely and logs no reason why.
On October 28, Stripe quietly added a pause button to its own customer portal. Set features.subscription_pause.enabled to true on a portal configuration and your subscribers get a native way to pause their own subscription — no code, no webhook, no UI you had to design. For a company that sells a cancellation flow for a living, this is the kind of change you can't skim past. Stripe just built a competing self-serve path to the exact moment our product exists to own.
That number is exactly why Stripe building a native pause path matters so much. Pause isn't a minor convenience feature — it's one of the highest-leverage retention moments in the whole subscription lifecycle, and now there are two separate doors into it: whatever you've built into your cancellation flow, and a new one Stripe ships for free that you don't control.
What actually shipped on October 28
The mechanics are simple, which is part of the point. Enable features.subscription_pause on a portal configuration, and the redesigned customer portal — the newer portal experience Stripe has been rolling out through 2026, not the legacy embed — gains a pause action for any subscription under that configuration. You can also deep-link straight to it: create a portal session with flow_data.type set to subscription_pause and the subscription ID in flow_data.subscription_pause.subscription, and the customer lands directly in the pause flow instead of the portal's main menu. That's the same deep-linking pattern Stripe already uses for subscription_cancel, subscription_update, and the customer_update flow we wrote about in September.
Under the hood, this calls the same pause mechanism Stripe introduced as a dedicated API in May 2026 — a real paused status on the subscription object, distinct from active, with no invoices generated while the pause is in effect. We covered that endpoint in detail in our piece on Stripe's paused subscription status. What's new isn't the pause mechanism itself. It's that Stripe now puts a button in front of the customer that calls it directly, with nothing of yours in between.
subscription_pause vs. subscription_cancel: not the same feature
Stripe built subscription_cancel and subscription_pause as parallel features in the same portal configuration object, but they're not peers in how much control you get over them. Pull up the API reference for both and the gap is obvious:
| Capability | subscription_cancel | subscription_pause |
|---|---|---|
| Reason capture | cancellation_reason object — fixed 5-option enum, plus custom feedback_options | None — no reason field exists on the object at all |
| Timing control | mode: immediately or at_period_end | No mode field — pause takes effect when the customer confirms |
| Proration handling | proration_behavior: none, create_prorations, always_invoice | No proration field — pausing stops billing, nothing to prorate |
| Duration control | N/A — cancellation is permanent by default | duration.type: indefinite, or interval_options up to 3 years |
| Default if you just flip "enabled" | No reasons collected unless you also enable cancellation_reason | A single one-month pause option, no reason collected |
The pattern is telling. Every control Stripe gave you over cancellation — why, when, how the money gets handled — is missing from pause. Pause shipped as a scheduling primitive: how long, and whether there's a limit. It did not ship as a retention-intelligence feature, even though pause is fundamentally a retention action.
The default is the shortest option, and nobody's reason gets recorded
Two details here are easy to miss if you just flip the flag and move on.
First, if you enable subscription_pause without configuring duration at all, Stripe defaults to interval_options with a single choice: one month. Not 30, 60, and 90 days as options — one month, full stop, unless you explicitly build the array yourself. A subscriber who needs six weeks, or who'd take an indefinite pause if offered one, doesn't see that choice. They see one button.
Second — and this is the part that should bother anyone running a cancellation flow — nothing about the pause event tells you why it happened. Compare this to what we wrote about the Feedback Options API Stripe shipped for cancellations two weeks earlier in the same Endive release: that feature exists specifically so you can collect a custom reason when someone cancels through the portal. Stripe clearly understands that capturing a reason has value. It built that capability for cancel and chose not to extend it to pause, which is either an oversight or a signal that pause is being treated as a billing-state toggle rather than a retention signal worth measuring.
Either way, the practical effect is the same: a subscriber can pause through the native flow, and the only thing your webhook on customer.subscription.paused will ever tell you is that it happened — not whether it was "too busy right now," "can't afford it this month," or "don't need it until next quarter." Those are three completely different subscribers who need three completely different follow-ups, and the native flow collapses all of them into a single undifferentiated event.
Share of stated cancel reasons across CancelFlow deployments. Source: why customers cancel.
Those four reasons alone call for different responses — a usage nudge, a temporary discount, a roadmap conversation, a feature workaround — and a pause offer that's actually matched to the reason converts far better than a generic one, exactly the logic our own post on pause vs. discount vs. downgrade lays out. Stripe's native button can't make that match. It has nowhere to store the information it would need to.
Two self-serve paths now lead to the same place
Here's the structural problem this creates. If you've built a pause offer into your own cancellation flow — shown it only to subscribers who selected a matching reason, tracked its acceptance rate, measured how many people who pause actually come back — that flow only runs when a subscriber goes through it. But subscribers reach Stripe's hosted portal through other doors too: a "manage billing" link in your app, a dunning email (our own guide to Stripe dunning explicitly recommends linking every failed-payment email straight to the portal), or a receipt footer. If subscription pausing is enabled on the portal configuration behind any of those links, a subscriber can now pause themselves the moment they land there — before your reason-based targeting ever sees them, and without your save-rate tracking ever recording the event as an offer you made.
That's not a reason to avoid the feature. A native pause option is still better for a subscriber than no pause option, and it's better than a cancellation you never get a chance to intercept. But it means the portal configuration itself has become a decision you need to make deliberately, not a default you inherit by checking a box.
What to actually do about this
Three concrete options, depending on how your product is set up:
- Leave it off on any configuration reachable outside your cancellation flow. If a given portal configuration is linked from dunning emails, receipts, or a generic "billing" link in your app, keep
subscription_pause.enabledfalse there. Let pause live only inside the flow where you actually capture a reason and can route it to the right follow-up. - If you do enable it, configure the duration deliberately. Don't ship the one-month default by accident. Match your interval options to what your own data says subscribers actually need — if your cancellation flow already offers 30/60/90-day pauses, mirror those exact windows so a subscriber gets the same choice regardless of which door they walked through.
- Treat the pause webhook as a blind spot, not a clean signal. Any
customer.subscription.pausedevent that didn't originate from your own flow should get flagged in your churn dashboard as reason-unknown, not folded into whatever bucket your flow-driven pauses land in. Mixing the two quietly corrupts every acceptance-rate number you're using to decide which offers actually work.
If you're trying to put a number on what a portal-only pause costs you in lost targeting, our retention rate calculator is a quick way to see how much a few extra points of blind, unmeasured saves are actually worth against your current churn baseline. And if your cancellation flow doesn't have a reason-matched pause offer in it yet, that's precisely the gap a tool like CancelFlow is built to close — pausing the right subscription, through the right offer, with the reason attached, instead of leaving it to whichever door the customer happens to walk through first.
Frequently asked questions
What is Stripe's new subscription pausing feature in the customer portal?+
It's a feature Stripe added to the Billing Portal in the October 28, 2026 Endive API release (2026-10-28.endive). Set features.subscription_pause.enabled to true on a customer portal configuration, and subscribers get a native pause action inside the redesigned customer portal — no custom code, no webhook handler, no UI you have to build. It sits alongside the portal's existing subscription_cancel and subscription_update features as a fourth self-serve action a customer can take without contacting you.
How do I enable and configure subscription pausing in Stripe's customer portal?+
Set features.subscription_pause.enabled to true when creating or updating a portal configuration through the Billing Portal Configurations API. By default, if you don't set features.subscription_pause.duration, customers get exactly one option: a one-month pause. To offer other lengths, pass duration.type as interval_options with an array of interval_options objects (each with an interval of day, week, month, or year, and an interval_count), up to a maximum total duration of three years. Setting duration.type to indefinite removes the cap entirely and lets the customer pause with no fixed end date. To send a customer straight to the pause flow rather than the portal's main menu, create a portal session with flow_data.type set to subscription_pause and the subscription ID in flow_data.subscription_pause.subscription.
Does Stripe's native portal pause feature collect a reason for pausing?+
No. The subscription_pause object in the portal configuration schema has exactly two sub-fields — enabled and duration — and neither has anything resembling the cancellation_reason object that subscription_cancel has supported for years, with its enabled flag, fixed list of five reason options, and feedback_options for custom text. A customer can pause through the native flow and Stripe records nothing about why beyond the fact that a pause event fired. Compare that to Stripe's own Feedback Options API, covered in our piece on <a href="/blog/stripe-feedback-options-api-cancellation-reasons">custom cancellation reasons</a> — reason capture exists for cancel, and Stripe chose not to extend it to pause.
How is this different from the dedicated pause/resume API endpoints Stripe shipped in May 2026?+
Those endpoints — POST /v1/subscriptions/:id/pause and its resume counterpart, covered in our post on Stripe's paused subscription status — are things your application calls deliberately, typically from a retention offer a customer accepts inside a flow you built. The October 28 portal feature is the opposite direction: it's Stripe's own hosted UI calling that same underlying pause mechanism on the customer's initiative, with no application code and no business logic of yours in the loop at all.
Stop losing subscribers today
One script tag. One function call. A live cancellation flow in under 10 minutes.
Start free trial →