Agora
Concepts

Concepts

The four ideas the library is built on — money is an integer, the gateway is behind one contract, a charge is a promise until the webhook, and the ledger is what makes trusting the webhook safe.

Four ideas carry the whole library. Everything else in these docs is a consequence of one of them.

Money is an integer, in the smallest unit

1990 is R$ 19,90. Never 19.90, never a float, never a string parsed at the boundary. The PaymentsDriver contract, the billing tables and every diagnostics payload speak the currency's smallest unit, and the conversion some gateway APIs demand — Asaas and AbacatePay want decimal reais — lives in exactly one place, inside those drivers. A gateway that already speaks minor units (Woovi does) converts nothing. See Money.

One contract, many gateways

Eighteen gateways — Stripe, Adyen and PayPal, Mercado Pago and Pagar.me, Pix-native Woovi and AbacatePay, Razorpay, Mollie and the rest — normalize onto the same PaymentsDrivercharge, refund, createSubscription, parseWebhook — and onto the same domain types. Your services never see a gateway SDK, which is what makes adding a gateway a config entry and swapping one a routing change. A driver also declares what it supports, so sending a card to a Pix-only gateway fails at the manager with a clear message rather than as an opaque error from someone else's API. See Routing.

A charge is a promise; the webhook is the money

charge() returns a PENDING payment. Nothing has been paid: the customer still has to scan the QR code or approve the card. The only thing that turns that promise into revenue is the gateway calling your endpoint. Granting access on the response from charge() is the single most expensive mistake in this domain, and the library's shape exists to make the correct path the easy one. See The payment lifecycle.

The ledger is what makes trusting the webhook safe

"Trust only the webhook" is only workable if a webhook is safe to receive twice — and gateways redeliver constantly: on a timeout, on a non-2xx, from a dashboard replay, from an ops script. Every event is written to an idempotency ledger before any work runs, so a redelivery stops at the door instead of double-granting. That ordering, not the handler, is the guarantee. See Idempotency.

On this page