Fintech & Payment Gateways

Design a Distributed Payment Gateway & Immutable Double-Entry Ledger (Stripe / Adyen)

Staff / Principal

Architect a mission-critical payment processing platform featuring idempotent charge capture, distributed Saga transactions, immutable double-entry ledger bookkeeping, and PCI-DSS tokenization vaults.

Production Scale: 100M Transactions/Day • $10 Billion Volume • Zero Double Charges

Functional Requirements

  • Process credit card charges, ACH transfers, and refunds with zero double billing
  • Enforce immutable double-entry ledger where sum(debits) === sum(credits) at all times
  • Send real-time webhook event notifications with guaranteed at-least-once delivery

Non-Functional Requirements

  • Strict ACID transaction consistency across financial accounts
  • PCI-DSS Level 1 compliance (Zero raw card numbers stored in application databases)
  • 99.999% availability with zero silent transaction drops

Capacity & Scale Estimation

Transaction Volume100 Million charges / day (~1,200 TPS, 10k peak)
Daily Monetary Volume$10 Billion processed daily
Ledger Storage Growth~500 GB / month of immutable append-only records
Webhook Dispatch300 Million webhook payloads / day

Core Architectural Components

1Card Tokenization Vault (Isolated HSM)

Hardware Security Module (HSM) encrypting PANs with AES-256-GCM, returning non-sensitive surrogate tokens to the core app.

2Idempotency Layer (Redis Cluster)

Stores `Idempotency-Key` hash with lock state; duplicate client requests within 24h return cached responses immediately.

3Payment Orchestrator & Saga State Machine

Coordinates multi-step checkout workflow (Authorize -> Tokenize -> Acquire -> Settle -> Notify) with compensating transactions.

4Immutable Double-Entry Ledger (PostgreSQL / CockroachDB)

Append-only relational ledger enforcing zero row updates; every monetary transfer creates equal debits and credits.

5Webhook Retry Dispatcher (Kafka + Dead Letter Queue)

Dispatches HTTPS webhooks to merchant endpoints with exponential backoff retries over 72 hours.

Architectural FAQs & Interview Deep Dives

How do Idempotency Keys prevent duplicate charges when network timeouts occur?

When a client sends `Idempotency-Key: abc-123`, the gateway attempts an atomic `SET NX` in Redis. If the key exists, it returns the in-progress state or cached result, preventing duplicate credit card authorizations.

What is the Double-Entry Bookkeeping rule in financial software architecture?

Every transaction must contain at least two entries: one account is debited and another is credited by the exact same amount (`sum(debits) - sum(credits) === 0`). Rows are append-only and never updated or deleted.

How does the Saga pattern manage distributed transaction failures in microservices?

Instead of slow 2-Phase Commits that lock databases across networks, a Saga executes local ACID transactions sequentially. If a step fails (e.g. Card Expired), compensating transactions execute in reverse order (e.g. Release Reserved Inventory).

What is PCI-DSS Tokenization and why is it mandatory?

Payment Card Industry Data Security Standard forbids storing Primary Account Numbers (PANs) in regular databases. Tokenization swaps the PAN for a random surrogate token, isolating cardholder data into a certified vault.

How do you handle merchant webhooks that fail to respond?

Webhook payloads are queued in Kafka. If a merchant server returns 500 or times out, the message enters exponential retry queues (1m, 5m, 15m, 1h, 6h, 24h) before moving to a Dead Letter Queue (DLQ).

How are currency exchange rates rounded to prevent micro-penny rounding errors?

Financial systems never use floating-point types (`float` / `double`). They store monetary amounts in integer minor currency units (cents / satoshis) or use arbitrary-precision decimal types (e.g. `BigDecimal`).