API Reference
Every endpoint below speaks JSON, lives under https://api.infraio.xyz
(prod) or https://api-dev.infraio.xyz (test), and authenticates via
HMAC-SHA256 — see Authentication
for request signing and Errors for the
error envelope shape.
This page lists the endpoints for merchant integrations. Where an endpoint has no page of its own, it’s described in the related concept page.
Endpoints under /b2b/v1/* are HMAC-signed with your secret
key (sk_…). This is the surface your backend calls. The merchant
dashboard and the hosted checkout use their own endpoints, which aren’t
part of the integration API.
Checkout
| Method | Path | Purpose | Notes |
|---|---|---|---|
POST | /b2b/v1/checkout-sessions/quick | Create a session in one call — order + checkout-session minted together. | See Quickstart for the request body and sample. |
POST | /b2b/v1/checkout-sessions | Create a session against an existing order. Use when your platform already has its own order model and you want one session per attempt. | The two-step flow. |
GET | /b2b/v1/checkout-sessions/by-order/{order_id} | List all sessions ever minted for an order. | Useful when a buyer abandoned a session and you want to surface the previous attempts in your dashboard. |
Orders
Orders are the timeless billable entity. A single order can back multiple checkout sessions (e.g. buyer abandons, retries).
| Method | Path | Purpose | Notes |
|---|---|---|---|
POST | /b2b/v1/orders | Create an order without a session. | Use when you want to send the buyer a payment link later instead of redirecting them immediately. |
GET | /b2b/v1/orders/{id} | Read a single order with line items + status. | Status: PENDING → PAID | PARTIAL_PAID | CANCELED. After refund: PARTIALLY_REFUNDED | REFUNDED. |
GET | /b2b/v1/orders/by-merchant/{merchant_id} | List your orders, cursor-paginated. | See Cursor pagination for the cursor protocol. |
PATCH | /b2b/v1/orders/{id}/cancel | Mark an unpaid order canceled. Emits order.canceled. | Fails if the order is already paid. |
PATCH | /b2b/v1/orders/{id}/reopen | Reverse an auto-cancel (canceled_reason=payment_timeout). | Useful if the buyer comes back after the TTL expired. |
Refunds
See Refunds concept page for the saga flow and token lifecycle.
Merchant-initiated
| Method | Path | Purpose | Notes |
|---|---|---|---|
POST | /b2b/v1/merchants/{merchant_id}/refunds | Merchant-initiated refund. Auto-approved (skips PENDING). | Emits payment.refund.approved immediately. |
Customer-initiated — refund-request tokens
The buyer fills the refund form on our hosted page; you only mint the token and deliver the URL. You can mint tokens from your backend (below) or from the merchant dashboard. Renewals and cancellations are handled in the dashboard.
| Method | Path | Auth | Purpose |
|---|---|---|---|
POST | /b2b/v1/merchants/{merchant_id}/refund-requests | HMAC (sk_…) | Mint a token from your backend. Body: {ref_type, ref_value, amount, ttl_seconds?, metadata?, hide_summary?, hide_header?}. ref_type is one of order_id / order_number / session_id / session_key; ref_value is the matching identifier. amount is required and locks the maximum the buyer can submit. Default TTL 30 min. Emits refund_request.created (source: b2b). |
Refund lifecycle (post-create)
Applies to both flows. The endpoints below operate on the refund
itself (id starts rfn_…), not the request token.
| Method | Path | Purpose | Notes |
|---|---|---|---|
GET | /b2b/v1/refunds/{id} | Read one refund. | Status: PENDING → APPROVED → EXECUTED | REJECTED. |
GET | /b2b/v1/refunds/by-merchant/{merchant_id} | List your refunds, cursor-paginated. | — |
POST | /b2b/v1/refunds/{id}/approve | Approve a PENDING refund (customer-initiated only — merchant-initiated lands APPROVED already). | Crypto: lands APPROVED, you call /submit-tx next. |
POST | /b2b/v1/refunds/{id}/reject | Deny a PENDING refund. | Emits payment.refund.rejected. |
POST | /b2b/v1/refunds/{id}/submit-tx | Crypto only — stamp the on-chain tx hash you broadcast. | Body: {tx_hash, network, token_address} — all three required. |
Catalog (read-only)
| Method | Path | Purpose |
|---|---|---|
GET | /v1/supported/networks | All chains InfraIO Pay can settle on (mainnet + testnet, filtered by env). |
GET | /v1/supported/tokens | All stablecoins on those chains. |
GET | /v1/supported/currencies | Currencies accepted for order.currency. |
Health
| Method | Path | Auth | Purpose |
|---|---|---|---|
GET | /health | None (public) | Liveness check. Returns {"status":"ok"}. Point your uptime monitors here. |
Cursor pagination
Every list endpoint accepts the same query params, returns the same envelope. Cursors are opaque and are used instead of offsets, so a page never shifts when a new row arrives while you’re paging.
| Query param | Type | Default | Notes |
|---|---|---|---|
cursor | string | — | Opaque — copy the previous response’s next_cursor verbatim. |
limit | int | 20 | 1..100. |
sort_dir | 'asc' | 'desc' | desc | Sort by (created_at, id). |
from / to | RFC3339 | — | Optional time-window filter. |
search | string | — | Free-text filter where supported. |
Response envelope:
{
"orders": [ /* page rows */ ],
"next_cursor": "eyJjcmVhdGVkX2F0IjoiMjAyNi0wNS0...",
"has_next": true
}has_next is always present. next_cursor is omitted when has_next
is false. Treat the cursor as an opaque string.
What’s missing from this page
This page covers the endpoints intended for merchant integrations. If you need an endpoint that isn’t listed, or an OpenAPI spec, contact support.