Skip to main content
An invoice is a single payment order. You create it, redirect the customer to the returned payment_url, and the invoice moves through its lifecycle to a terminal status. Confirm the result via a webhook or by reading the invoice.

Before you create

A create call must satisfy every condition below. Each maps to a specific error (see Errors).
The currency code must exist and be active (404 CURRENCY_NOT_FOUND) and be one of the currencies enabled for your business (422 CURRENCY_NOT_ALLOWED). See Allowed currencies.
The amount must fall within the min/max range of at least one active payment method for that currency. Otherwise 422 AMOUNT_OUT_OF_RANGE.
callback_url, success_url, and fail_url must each be resolvable — from the request or from your business settings. Missing ones → 422 INVOICE_URLS_MISSING with details.missing.
A customer may not exceed the platform’s cap of open unpaid invoices within a rolling window. Otherwise 429 TOO_MANY_UNPAID_INVOICES.

Allowed currencies

Each business is provisioned with a set of enabled currencies. A currency that exists globally but isn’t enabled for you returns 422 CURRENCY_NOT_ALLOWED.
Don’t hardcode currencies. Discover what you can actually charge from GET /external/payment-methods — each method carries its currency, min_amount, and max_amount. That endpoint is the source of truth for both allowed currencies and valid amount ranges.

Create an invoice

POST /external/invoices201

Request

Your own order id (1–128 chars). Used for idempotency and to look the invoice up later.
Your identifier for the paying customer (1–128 chars). Used for the unpaid-invoice limit.
Base order amount in fiat. Positive, at most 2 decimal places. Send as a string: "1050.00".
Currency code, e.g. "UAH" (2–16 chars). Must be active and allowed for your business.
Optional description (≤255 chars).
HTTPS webhook URL for settlement callbacks. Falls back to your business settings if omitted.
HTTPS URL the customer returns to after a successful payment. Falls back to settings.
HTTPS URL for a failed/abandoned payment. Falls back to settings.
URL resolution priority is request → business settings. Set defaults once in the dashboard and omit them per call, or override per invoice. An empty string counts as missing.

Response

Our order id. Look the invoice up by this or external_id. Base order amount, unchanged for the invoice’s life. What the customer pays, including client commission. null until a method is chosen. { id, code, name, symbol }. One of pending, success, expired, canceled, fail. Ready-to-use hosted payment link. Returned only on create and read-by-creator. When the invoice auto-cancels if unpaid (platform-configured TTL).
Redirect to payment_url right away, or persist it. The invoice auto-cancels at expires_at if the customer hasn’t paid — after that, create a new invoice.

Errors

Idempotency

Creating is idempotent on external_id, scoped to your business:
  • Same external_id, still pending, same amount + ****currency → returns the existing invoice (same payment_url). Safe to retry on network errors.
  • Same external_id, but different params or already terminal409 INVOICE_ALREADY_EXISTS with details.status. A closed order is never revived.
Use a stable external_id per order and a retry can never double-charge or create a duplicate.

List invoices

GET /external/invoicesPage<InvoiceExternalRead> 1-based page number. Items per page. Filter by status: pending, success, expired, canceled, fail. Filter by currency code, e.g. UAH. Returns the standard page envelope; each item is the same shape as Get an invoice.

Get an invoice

GET /external/invoices/{ident}InvoiceExternalRead {ident} is either our order_id (the uuid) or your external_id — both resolve within your business.
Beyond the create fields, the read includes the settlement state (all null until the customer picks a method): When the invoice reached a terminal state. { name, logo_url } — the method the customer chose. Fiat-per-USDT rate snapshot of the deal. USDT credited to you. Populated only on success. Whether the paid amount was corrected during a dispute.
Present only when is_adjusted.
amount stays the original order amount even after an adjustment. The real settled figures live in settled_amount_usdt and adjustment. Reconcile payouts against those, not against amount.

Invoice webhooks

Two endpoints inspect and re-trigger the settlement callbacks for an invoice:
  • GET /external/invoices/{ident}/webhooks — delivery history for the invoice.
  • POST /external/invoices/{ident}/resend-webhook — send the latest delivery now.
Full payload shape, signing, retries, and error codes are on the WebHooks page.