/v1/fx:
- Indicative rate (
GET /v1/fx/rate) — read-only, cheap, non-binding. For display. - Lockable quote (
POST /v1/fx/quote) — binding rate for a short window. Use when you need price certainty before committing. - Exchange (
POST /v1/fx/exchange) — executes a locked quote, moves funds between your own merchant balances in different currencies.
POST /v1/payouts with different source_currency and dest_currency.
When you need each
| You want to… | Use |
|---|---|
| Show a customer what a payout will cost them in their currency | GET /v1/fx/rate |
| Lock in a rate before showing “send” to the customer | POST /v1/fx/quote then POST /v1/fx/exchange |
| Convert your own balance from one currency to another | POST /v1/fx/quote then POST /v1/fx/exchange |
| Send a payout that debits one of your currencies and credits another on the beneficiary’s side | POST /v1/payouts with different source/dest currencies — FX is automatic |
Indicative rates
For display-only use. Two currencies, optional sell amount:mid_market_rate— raw interbank ratecustomer_rate— mid-market adjusted by your pricing plan’s FX markup (fx_markup_bps)buy_amount— computed usingcustomer_rate
Lockable quotes
When you need certainty:sell_amount OR buy_amount — Anton computes the other side at the quoted rate. The response includes an id (fxq_...) and an expires_at. Execute before that moment.
Executing an exchange
Exchange is idempotent:- Debits
sell_amountfrom your merchant balance insell_currency. - Credits
buy_amountto your merchant balance inbuy_currency. - Records an
fx.exchange.*webhook event and an audit entry.
410 quote_expired — request a new quote. Rate-limited at 10/min per IP.
FX on cross-currency payouts
You typically don’t call/v1/fx/* explicitly when sending a payout — Anton handles it transparently:
source_amount using current pricing (rate + markup + fee + buffer), debits your USD balance, converts, and pays the beneficiary in EUR via SEPA.
The returned Payout carries FX detail — exchange_rate, fee, fee_currency, buffer_amount, buffer_currency. The buffer_amount is a cross-currency rate buffer held during processing and released on settlement.
When to lock separately: if your application needs to show the exact source_amount to the end user before they confirm, pre-lock via POST /v1/fx/quote and surface the quote’s customer_rate. The payout will use the same corridor pricing but isn’t bound to the quote unless you execute against the locked quote explicitly (via the merchant account funding path — typically dashboard-driven).
Listing exchange history
sell_currency, buy_currency, created_after, created_before. Cursor-paginated.
Each exchange has a status (pending / completed / failed) and, if it was created to fund a cross-currency payout, a payout_id.
What can go wrong
422 insufficient_balance on exchange
422 insufficient_balance on exchange
Your sell-currency balance can’t cover the exchange. Fund your balance or size the exchange down.
410 quote_expired
410 quote_expired
The lock window passed. Request a new quote — the rate may have moved in either direction.
422 currency_not_supported
422 currency_not_supported
Anton doesn’t currently support FX in the requested pair. See
GET /v1/currencies for what’s available.503 locked_rate_unavailable
503 locked_rate_unavailable
502 fx_rates_unavailable
502 fx_rates_unavailable
Subscribe to FX webhooks
fx.quote.createdfx.exchange.createdfx.exchange.completedfx.exchange.failed
Next steps
Send a payout
Including cross-currency payouts that use FX transparently.
Handle webhooks
React to
fx.* events on your balance-sheet reconciliation.