Cashout
Cashout pays fiat directly to a recipient's bank account, debiting your crypto fund. You name the recipient yourself, in the order itself.
- Quote it —
review-cashout. - Create it —
create-cashout. - Track it —
orders/details, plus a webhook.
The user must be KYC-verified first. See KYC. Cashout and scan-to-pay share the same order lookup, the same order object, and the same webhook.
Quote a cashout
POST /api/v2/orders/review-cashout
Signed string
partnerCode|userEmail|fiatCurrency|fiatAmount|cryptoCurrency|<secretKey>
Request — every field is required.
| Field | Type | Notes |
|---|---|---|
partnerCode | string | |
userEmail | string | The end user. |
fiatCurrency | string | VND, PHP, IDR… |
fiatAmount | number | What the recipient receives. No decimals for VND and IDR, up to two for PHP; see Amount precision. |
cryptoCurrency | string | The crypto to debit — USDT. |
signature | string |
Response data
| Field | Type | Notes |
|---|---|---|
fiatAmount | number | Echoed from your request. |
currency | string | The crypto code. |
price | number | |
tokenAmount | number | The crypto that will be debited. |
totalPayment | number | |
processingFee, systemFee | number | |
signature | string | Over fiatAmount|currency|price|tokenAmount|totalPayment|secretKey. |
The live minimum and maximum reach you through errors 24 and 25, whose messages carry the
current limit.
Errors — 46 SERVICE_NOT_AVAILABLE, 24 / 25 (below min / above max), 16
AMOUNT_OUT_OF_RANGE (below the payment provider's own floor, 10,000 VND for Vietnam), 7
PARTNER_INSUFFICIENT_BALANCE, 9 SERVICE_UNDER_MAINTENANCE, plus the KYC codes (34, 59, 60,
61, 62, 64) and the shared ones.
Create a cashout
POST /api/v2/orders/create-cashout
Signed string
partnerCode|externalOrderId|userEmail|cryptoCurrency|fiatCurrency|fiatAmount|<secretKey>
Cashout has its own string, with different fields and a different order from scan-to-pay's. It signs
cryptoCurrency and fiatCurrency, while the recipient's bank details travel in extendInfo,
outside the signature.
If fiatCurrency or fiatAmount is omitted, its segment becomes the literal text undefined, and
the order fails with 46. Include both fields in every request.
Request
| Field | Type | Required | Notes |
|---|---|---|---|
partnerCode | string | Yes | |
externalOrderId | string | Yes | Your unique id, and the idempotency key. |
userEmail | string | Yes | Must be KYC-verified. |
cryptoCurrency | string | Yes | The crypto to debit — USDT. |
fiatCurrency | string | Yes | Omitting it is not rejected as a missing field, and no default is applied. See above. |
fiatAmount | number | Yes | Same. |
extendInfo | object | Yes | The recipient. |
webhookSecretKey | string | No | Without it the order settles silently, read through orders/details. |
signature | string | Yes |
extendInfo — the recipient
| Field | Type | Required | Notes |
|---|---|---|---|
recipientName | string | Yes | |
recipientNumber | string | Yes | The bank account number. |
recipientBankCode | string | Yes | From the bank list. |
transferContent | string | No | The transfer remark. Unaccented letters only, where the provider checks it. |
recipientType | string | No | When sent, it must be a recognised value; an unrecognised one returns 5. |
{
"partnerCode": "ACME",
"externalOrderId": "acme-co-1042",
"cryptoCurrency": "USDT",
"fiatCurrency": "VND",
"fiatAmount": 5000000,
"webhookSecretKey": "81663eae...",
"extendInfo": {
"recipientName": "NGUYEN VAN A",
"recipientNumber": "0123456789",
"recipientBankCode": "VCB",
"transferContent": "ALIX CASHOUT 1042"
},
"signature": "I7XDfTngWIraq...=="
}
Response data — the order object, with type: "CASHOUT".
For a cashout, tokenTransfer.address, tokenTransfer.network and bankTransfer.qrUrl are
null; the payout goes straight to the recipient's bank account.
Errors — everything review-cashout can return, plus:
11 DUPLICATE_TRANSACTION_ID | externalOrderId is already used. |
13 WEBHOOK_SECRET_NOT_FOUND | webhookSecretKey matches no registered endpoint. Checked before anything else, so the order is not created. |
18 INVALID_BANK_ACCOUNT | extendInfo is missing, or the account could not be verified. |
56 BANK_NOT_SUPPORTED | recipientBankCode is not in the provider's list. |
17 INVALID_TRANSFER_CONTENT | transferContent has accents or special characters. |
27 USER_EMAIL_INVALID | userEmail is malformed. |
5 INVALID_REQUEST_DATA | recipientType is not a recognised value. |
12 TRANSACTION_CREATE_FAILED | The payout failed after the order was created. You are already refunded, and data holds the order. |