REST API
REST API
Every endpoint, with real requests and responses. New here? Start with the Quickstart; Python users can skip the HTTP and use the SDK.
Base URL and authentication#
The public sandbox is https://sandbox.whire.ai. Every example on these pages was produced against a running deployment with the simulated rail on.
Send your key on every request as X-API-Key: <key> (or Authorization: Bearer <key>). Three paths need no key: /api/health, /api/capabilities, /x402/supported. A shared sandbox may run with authentication switched off; then no key is needed anywhere.
Every response is JSON:
{ "ok": true, "data": { ... } }
{ "ok": false, "error": "what went wrong, in words" }Errors are 400 with a message written to be read, 401 for a missing or wrong key, 404 for an unknown route.
Start with capabilities:
{ "authorization": true, "settlement": true, "simulated": true, "environment": "SANDBOX",
"note": "This deployment authorizes payments and settles them in simulation. No money moves." }settlement says whether the deployment moves money at all, simulated whether that money is simulated (see Simulation).
Endpoints#
| Method | Path | |
|---|---|---|
| GET | /api/health |
Liveness. |
| GET | /api/capabilities |
What this deployment can do. |
| POST | /api/payers |
Sign up a payer. |
| POST | /api/payers/{id}/activate |
Record the verification decision. |
| POST | /api/payers/{id}/funding-sources |
Add an account the payer can be debited from. |
| POST | /api/payers/{id}/suspend |
Suspend a payer: no new mandates. |
| GET | /api/payers/{id} |
Read a payer. |
| GET | /api/payers |
List payers. |
| POST | /api/beneficiaries |
Register who can be paid. |
| POST | /api/validate-iban |
Check an IBAN's format and checksum. |
| POST | /api/mandates |
Sign a mandate. |
| POST | /api/mandates/{id}/validate |
Run the ten checks against a possible payment without deciding anything. |
| POST | /api/mandates/{id}/revoke |
Revoke a mandate. |
| GET | /api/mandates/{id} |
Read a mandate. |
| GET | /api/mandates |
List mandates. |
| POST | /api/authorize |
Ask whether a payment may proceed. |
| POST | /api/authorize/verify |
Verify a receipt you were handed. |
| POST | /api/payouts |
Create a payout draft under a mandate. |
| POST | /api/payouts/{id}/submit |
Send the draft to KYC review. |
| POST | /api/payouts/{id}/events |
Record a provider decision yourself when no provider is configured: kyc_approved, kyc_rejected, payment_processing, payment_paid, payment_failed, payment_returned. |
| POST | /api/payouts/{id}/confirm |
Human confirmation before execution. |
| POST | /api/payouts/{id}/execute |
Send the payout through the rail. |
| GET | /api/payouts/{id} |
Read a payout with its history. |
| GET | /api/payouts?status=paid |
List payouts; ?status= filters. |
| GET | /api/simulation |
The simulated rail: scenarios, delay, every simulated account with its balance. |
| POST | /api/reset |
Empty the store and the simulated ledger. |
Idempotency#
Send Idempotency-Key: <uuid> on any POST that creates something. Same key and body again → the stored response is replayed (Idempotent-Replay: true). Same key while the first is still running → 409. Same key, different body → 422. Keys live 24 hours.
Limits#
- State is in memory; a redeploy or
POST /api/resetwipes it. - One key per deployment: every caller sees every record.
- No rate limiting, no webhooks.
- EUR only.