
Recurring Payment System Development: Subscriptions, Dunning, and Retry Logic
| What This Guide Covers01 What a recurring payment system is02 Why failed payments quietly kill subscription revenue03 Core architecture of a subscription billing system04 The subscription lifecycle, end to end05 Dunning: recovering failed payments06 Retry logic: soft declines, timing, and limits07 Preventing failures before they happen08 Compliance for recurring payments09 Cost, team, and how to build it10 Proof: a subscription backend we rebuilt |
As the FinTech Engineering Lead at Acquaint Softtech, a software product development partner, I see the same pattern in most subscription businesses: the checkout works, but the renewals leak. This guide shows how to build a recurring payment system that bills reliably and, just as importantly, recovers the payments that fail.
A strong recurring payment system needs four things working together, a subscription engine that manages plans and state, a scheduler that charges on time, dunning that recovers failed payments, and retry logic that is smart about which failures to retry and when. Skip the last two and you lose revenue you already earned.
The benchmarks here are attributed to their sources, so you can verify them. This guide draws on subscription platforms Acquaint Softtech has built as an Official Laravel Partner, with 1,300+ projects, 70+ in-house engineers, and clients across the USA, UK, Europe, and Australia who deploy dedicated teams within 48 hours of a brief.
What a recurring payment system is
A recurring payment system automates everything that happens after a customer subscribes: it stores the plan and price, charges the card on schedule, handles trials and proration, tracks whether the subscription is active or past due, and recovers payments that fail. It replaces manual invoicing with a self-running billing cycle.
The difference from one-time payments is state. A single charge either succeeds or fails and is done. A subscription is a living object that moves between states over months, and most of the engineering effort goes into handling the unhappy paths, not the first successful charge.
See also: Schema-per-Tenant Migrations: Running Migrations Across Thousands of Tenants
Why failed payments quietly kill subscription revenue
Failed payments, not cancellations, are the hidden half of subscription churn. Because these customers never chose to leave, most of the lost revenue is recoverable, which makes billing the cheapest churn to fix and dunning the highest-ROI system you can build.
- Involuntary churn is 20 to 40% of total subscription churn, caused by failed payments rather than cancellations (Recurly, Paddle).
- Stripe attributes about 25% of lapsed subscriptions purely to payment failure, and estimates roughly 9% of MRR is lost to it annually.
- A well-run dunning process recovers around half of failed charges, and best-in-class programs recover 70 to 85% (Recurly, Chargebee).
The takeaway is simple: if you do not measure your voluntary versus involuntary churn split, you cannot tell whether your problem is the product or the billing system. A rising involuntary share is an engineering problem wearing a product problem’s clothes.
See also: Schema-per-Tenant Migrations: Running Migrations Across Thousands of Tenants
Core architecture of a subscription billing system
A subscription billing system is a set of cooperating services, not a single charge call on a schedule. The components below each own one responsibility, which is what keeps billing correct when charges fail, plans change, and customers upgrade mid-cycle.
| Component | What it does |
| Subscription engine | Tracks plan, price, and state (trial, active, past due, canceled) |
| Plan and pricing catalog | Defines tiers, add-ons, usage rates, and proration rules |
| Scheduler | Triggers renewal charges on time, at scale, without duplicates |
| Gateway connector | Sends charges and reads results from Stripe, Razorpay, or others |
| Dunning engine | Runs retries and customer notifications on failed payments |
| Ledger and invoicing | Records every charge, credit, and refund for finance |
| Webhooks and portal | Sync events to your app and let customers self-manage billing |
The scheduler, ledger, and dunning engine are the parts that must be exactly correct under failure and retry, so they belong in disciplined backend development, where idempotency prevents double charges and a clean ledger keeps finance and access control in agreement.
The subscription lifecycle, end to end
A subscription moves through a predictable set of states, and your system’s job is to handle every transition, including the failures. The lifecycle below is what the engine tracks for each customer.
- Sign up or trial: the customer subscribes, often starting a free trial with no charge.
- Active: the first successful charge activates the subscription and grants access.
- Renewal: the scheduler charges the saved payment method at the start of each cycle.
- Past due: a failed renewal moves the subscription to past due and starts dunning.
- Recovered or canceled: a retry or updated card recovers it, or the grace period ends and it cancels.
Around these states sit proration for mid-cycle upgrades and downgrades, credits for refunds, and grace periods that keep access on while recovery is attempted. Handling proration correctly is a common source of billing disputes, so it deserves real test coverage.
Dunning: recovering failed payments
Dunning is the automated process of retrying a failed payment and prompting the customer to fix their billing details before the subscription cancels. Done well, it reads as a helpful nudge rather than a demand, because most failures are mechanical, not a decision to stop paying.
The highest recovery comes from combining three layers, not relying on one. Recurly reports the combination recovers around 70% of failed payments, well above any single tactic used alone.
- Smart retries: re-attempt the charge on a schedule tuned to the decline reason and timing.
- Dunning emails: a sequence asking the customer to update their card, with clear, calm copy.
- Card updater: automatically refresh expired or reissued cards so many failures never happen.
Pre-dunning is the underrated fourth move: email customers before a known card expiry, typically 30 and 7 days ahead. These messages get opened more because the customer is not yet in a something-went-wrong mindset.
Retry logic: soft declines, timing, and limits
The single most important rule of retry logic is to retry soft declines and never retry hard declines. A soft decline is temporary and worth retrying; a hard decline is permanent, and retrying it wastes attempts and can trigger card-network penalties.
| Decline type | Examples | Action |
| Soft (retry) | Insufficient funds, issuer timeout, do-not-honor | Retry on a smart schedule |
| Hard (stop) | Stolen card, invalid account, closed account | Stop and ask for a new card |
What makes a retry smart
- Decline-aware: read the decline code and only retry the ones worth retrying.
- Well-timed: spread attempts across the grace window, for example days 1, 3, 5, and 7, and favor times money is likely present, such as after payday.
- Idempotent: use idempotency keys so a retry never accidentally double-charges a customer.
- Within limits: card networks cap how many times a declined recurring charge may be retried, and exceeding it can incur fines, so track attempts per invoice.
Preventing failures before they happen
The cheapest failed payment is the one that never happens, so prevention beats recovery. Two mechanical fixes stop a large share of failures at the source before any retry is needed.
- Card account updater: Visa and Mastercard updater services refresh expired and reissued cards automatically, which the card networks associate with a 40 to 60% cut in expiry-related involuntary churn.
- Network tokenization: store a network token instead of the raw card so the credential keeps working when the physical card changes.
Billing cadence matters too. ProfitWell finds annual billing carries roughly 12 times lower involuntary churn than monthly, because there is only one charge a year that can fail. Offering a backup payment method is another simple, effective safeguard.
Compliance for recurring payments
Recurring payments carry region-specific rules that your system must handle, or renewals will be declined or blocked. The two that catch most global teams are European strong authentication and India’s mandate rules.
- Europe (PSD2 SCA): the initial subscription setup usually needs Strong Customer Authentication via 3DS2. Later merchant-initiated charges are exempt, but only if you flag them correctly as MIT.
- India (RBI e-mandate): recurring card payments need e-mandate registration, a pre-debit notification to the customer 24 hours before each charge, and per-transaction limits.
- PCI-DSS: store network tokens, not raw card numbers, so the saved credential that powers every renewal never puts you in extra compliance scope.
Cost, team, and how to build it
The first decision is build versus buy. Tools like Stripe Billing, Chargebee, or Recurly cover standard subscriptions quickly, so a custom build makes sense when you need complex or usage-based pricing, multiple gateways, or billing logic those tools cannot express.
A custom build is a specialist effort: backend engineers for the subscription engine and ledger, a scheduler and queue for reliable renewals, and integration work for gateways and webhooks. Teams that hire API developers with payments experience get idempotent retries, webhook handling, and reconciliation right the first time. Scoping the pricing model and edge cases through a short discovery workshop prevents costly rework once real subscriptions are live.
Proof: a subscription backend we rebuilt
Acquaint Softtech restructured the backend of Juna AI, a Berlin-based AI company, to support true multi-tenancy and cleaner subscription management for enterprise customers. This account is drawn from the client’s 5.0 out of 5 Clutch review.
The team improved role-based access control and reworked the subscription logic to support multiple sites, users, and usage tiers under a single enterprise account. The work was done on a live production backend without interrupting active users, using Laravel for multi-tenancy, background processing, and authorization.
After the engagement, onboarding new enterprise customers became smoother, permission issues became rare, and, in the client’s words, subscription handling became far more predictable for both billing and access control. Predictable billing state is exactly what a recurring payment system lives or dies on, and it is the discipline this guide argues for throughout.
Short answers to common questions
What is dunning in recurring payments?
A: Dunning is the automated process of retrying a failed subscription charge and emailing the customer to update their card before the subscription cancels. Combining retries, emails, and a card updater recovers the most revenue.
Should I retry every failed payment?
A: No. Retry soft declines like insufficient funds, but never retry hard declines like a stolen or closed card. Retrying hard declines wastes attempts and can trigger card-network penalties.
How much revenue can dunning recover?
A: A well-run dunning process typically recovers around half of failed payments, and best-in-class programs reach 70 to 85%, because most failures are mechanical and the customer never meant to leave.
What is the best retry schedule?
A: Spread a few attempts across the grace period, for example days 1, 3, 5, and 7, timed for when funds are likely available. Read the decline code so you only retry failures worth retrying.
Do I need SCA or RBI rules for recurring payments?
A: Yes, if you bill in those regions. Europe needs Strong Customer Authentication at setup, and India needs RBI e-mandate registration with a pre-debit notification 24 hours before each charge.
Should I build or buy a recurring billing system?
A: Buy a tool like Stripe Billing for standard subscriptions. Build custom when you need complex or usage-based pricing, multiple gateways, or billing logic those tools cannot express.


