Building payment systems without betting the business on one provider

Payments are promises, not money.

Payments sit at the centre of almost every digital business, yet they remain widely misunderstood. At WebExpo 2025, Alvaro Duran Barata, senior software engineer at Happening and formerly in the fintech tribe at Kiwi.com, delivered a detailed and uncompromising talk on why payment systems fail and how engineers can design them to be resilient, scalable, and adaptable.

He began with a warning that set the tone for the session: “Maybe the worst kind of problems are the ones you don’t know you have.”

From the start, he challenged the widespread belief that payments are a solved problem best handled by a single provider.

“Why do you have a job?”

Alvaro shared the reaction he often gets when he tells people he builds payment systems: “They always ask, why don’t you just use Stripe?”

Stripe, he noted, is a great place to start. But as businesses grow, relying on a single payment service provider (PSP) becomes a structural risk. Providers fail, sometimes publicly and sometimes without explanation. He cited recent outages and real-world examples where even entire countries were forced back to cash-only transactions.

Credit: Alvaro Duran Barata

The deeper issue is control. By outsourcing payments entirely, companies hand over their most crucial bottleneck to a third party with different priorities. Research shows that half of businesses depend on a single PSP, and many experience higher fees, lower success rates, or sudden disruptions. These are not exceptions; they’re common occurrences.

Payments are not movements of money

One of the talk’s key ideas was redefining what a payment actually is.

“A payment is a promise made by other parties about a movement of money.”

When a customer completes a purchase, money doesn’t move immediately. Instead, systems exchange guarantees between banks and networks such as Visa or Mastercard. This distinction changes how systems should be designed.

Alvaro broke payments into three distinct stages: authentication, authorisation, and confirmation. This separation allows systems to manage fraud, insufficient funds, and fulfilment, rather than compressing everything into one “charge” action.

The danger of treating all payments like cards

A recurring pattern Alvaro has observed is assuming all payments behave like card payments. Even major platforms have made this mistake. Early in its history, Stripe designed abstractions for cards that later became fragile as new payment methods emerged.

Credit: Alvaro Duran Barata

Bank transfers, delayed authorisations, and cryptocurrencies introduced asynchronous behaviour that broke systems expecting instant responses. The result was unnecessary complexity, brittle state machines, and poor user experiences, such as frozen funds or incomplete orders.

To address this, Alvaro proposed a taxonomy based on two axes: whether user action is required, and whether authorisation happens immediately or later. This framework allows systems to adapt dynamically instead of being constrained by early assumptions.

Just-in-time categorisation

A core design insight from the talk was what Alvaro called “just-in-time categorisation”. Rather than defining how a payment behaves ahead of time, systems should infer it from the provider’s actual response.

“I can let the code or the provider’s response decide what category I’m in.”

This approach reflects how modern payments really behave: success, failure, and pending states can arrive either synchronously or asynchronously, and systems must handle both seamlessly.

When providers answer more than once

Distributed systems rarely behave as neatly as diagrams suggest. Payment providers often send duplicate results via direct responses and webhooks.

“The provider is just making sure you get the response, and it’s fine if you get it twice.”

Without safeguards, this can lead to double charges. Alvaro stressed that engineers must assume duplicate messages are normal and design idempotency and mutual exclusion into their systems from the start.

Payments don’t depend on each other

As systems scale globally, teams often worry about coordinating payments across regions. Alvaro challenged this instinct.

“Payments don’t depend on one another… they are interleaved.”

Even at tens of thousands of transactions per second, the same payment never happens in multiple regions simultaneously. Recognising this allows engineers to use regional locks instead of global ones, simplifying the architecture and improving performance.

Why payments engineering still matters

Alvaro closed by returning to his opening question: why do payment engineers still exist?

Because many still mistake payments for money movement. Because systems still assume all payments behave like cards. Because PSPs will send duplicate messages. And because payments scale differently from most other systems.

“This is one of the most interesting and exciting industries to operate and to build stuff for.”

For those who want to dig deeper, Alvaro recommended his newsletter The Payments Engineer Playbook and his book The Databases of Money: Designing Payment Applications.

The full recording and slides from his talk:

This Site Uses Cookies

For processing purposes, your consent is required, which you express by selecting "Allow all." You can also customise your settings.