Each test is 5 questions with varying difficulty.
AI Prep covers AI Agents, Generative AI, ML Fundamentals, NLP & LLMs and a lot more, with adaptive tests and daily challenges. Fully offline on Android. Free to try, one-time unlock for lifetime access.
Designing a payment system is a classic high-stakes system design interview topic that tests a candidate's ability to handle distributed state, data integrity, and extreme reliability. In 2026, as fintech infrastructure becomes more modular, interviewers expect candidates to move beyond simple API design and demonstrate deep knowledge of transactional consistency, auditability, and fault tolerance. This topic is essential for Backend, Site Reliability, and Platform Engineers working on financial services. Junior candidates are expected to understand basic ACID properties and simple API flows. Senior candidates must demonstrate expertise in handling network partitions, implementing idempotent retries, managing double-entry ledgers, and designing asynchronous reconciliation pipelines to ensure data consistency across heterogeneous systems. Interviewers ask about this to gauge your ability to manage 'money-at-risk' scenarios where data loss or race conditions result in direct financial liability.
A payment system is the backbone of any commercial platform. Unlike standard CRUD applications, payment systems cannot tolerate data loss, duplicate charges, or inconsistent states. A single bug can result in direct financial loss, regulatory non-compliance, and loss of customer trust. In 2026, with the rise of real-time payment rails and global cross-border transactions, the complexity has shifted toward managing distributed state across multiple microservices and third-party gateways. This is a high-signal interview topic because it forces candidates to confront the reality of distributed systems: network failures are inevitable, and 'exactly-once' processing is a myth that must be approximated through idempotent design and robust reconciliation. A strong candidate will immediately pivot to discussing how to maintain a source of truth using double-entry ledgers and how to handle failures gracefully using the Outbox pattern. A weak candidate often ignores the 'what happens if the network fails after the charge but before the database update' scenario, which is the core of the problem.
The architecture follows a decoupled, event-driven model to ensure high availability and durability. The core is a ledger service that maintains the source of truth, protected by strict ACID compliance. External requests are throttled and validated before being passed to an orchestration layer that manages the payment lifecycle via state machines.
[Client Request]
↓
[API Gateway (Rate Limiting)]
↓
[Payment Orchestrator (Saga)]
↙ ↘
[Ledger Service] [Outbox Table]
↓ ↓
[PostgreSQL (ACID)] [CDC/Relay]
↓
[Message Broker]
↓
[External Payment Gateway]
Clients generate a UUID for every request. The server stores this key in a unique constraint table before processing.
Trade-offs: Adds storage overhead; requires cleanup jobs for old keys.
Decomposes a transaction into a series of local transactions with compensating actions for failures.
Trade-offs: Complex to implement; requires careful handling of partial states.
Writes events to an 'outbox' table in the same transaction as the business data, then relays them to a broker.
Trade-offs: Requires a CDC (Change Data Capture) tool or polling mechanism.
| Reliability | Use multi-region databases and circuit breakers to isolate failures from external payment providers. |
| Scalability | Partition ledger tables by account_id; use Kafka partitions for parallel event processing. |
| Performance | Cache idempotency keys in Redis; use asynchronous processing for non-critical path tasks. |
| Cost | Minimize database storage by archiving old ledger entries to cold storage. |
| Security | Implement PCI-DSS compliance; use tokenization for card data; enforce mTLS for service communication. |
| Monitoring | Track 'payment success rate', 'reconciliation discrepancy count', and 'latency of external calls'. |
A payment system is strictly transactional and must maintain financial integrity (the ledger). An order system tracks state changes (e.g., 'shipped', 'delivered') which are less sensitive to atomic consistency than moving money between accounts. Payment systems require double-entry bookkeeping, whereas order systems typically use single-state records.
It depends on the component. The ledger must be strongly consistent to prevent double-spending. However, downstream systems like analytics, reporting, or notification services can be eventually consistent. The key is ensuring the source of truth (the ledger) is always accurate.
Dual-writes (writing to a DB and then a message broker) are prone to partial failures where one succeeds and the other fails. The Outbox pattern ensures both are committed in a single database transaction, guaranteeing that the message will eventually be sent.
2PC is a synchronous, blocking protocol that requires all participants to agree before committing, which is slow and fragile in distributed systems. Sagas are asynchronous, non-blocking, and use compensating transactions to handle failures, making them much more scalable.
Conversion should be treated as a separate transaction. You record the source currency debit, the destination currency credit, and a separate entry for the exchange rate and fees applied, ensuring the ledger remains balanced in both currencies.
It acts as a safety net. Since distributed systems can fail in unpredictable ways, reconciliation compares the internal state against the external gateway's records to identify and resolve discrepancies that occurred due to network timeouts or system bugs.
While possible, it is generally discouraged for the core ledger. Relational databases (RDBMS) provide ACID compliance and strong consistency out of the box, which are non-negotiable for financial systems. NoSQL is better suited for high-volume, non-financial data like logs or user profiles.
You shouldn't rely on the client. If a key is missing, the server should generate a deterministic key based on the request parameters (e.g., hash of user_id, amount, and timestamp) or reject the request, forcing the client to implement proper idempotency practices.
It is an action that undoes the effect of a previously successful step in a Saga. For example, if a payment succeeds but the inventory update fails, the compensating transaction would be a refund to the user.
Use database sharding by account_id to distribute the load. Additionally, use batching to group multiple small transactions into a single database commit, reducing the overhead of transaction logs.
AI Prep covers AI Agents, Generative AI, ML Fundamentals, NLP & LLMs and a lot more, with adaptive tests and daily challenges. Fully offline on Android. Free to try, one-time unlock for lifetime access.