FAQ
Should I use Hosted Checkout or API Mode?
Use Hosted Checkout unless the payment experience must live entirely inside your own product. Hosted is the smallest, safest surface — no payment UI to build, no IP allowlist. Choose API Mode when you render your own page and can call from allowlisted servers. See Checkout Modes.
Can I fulfil an order from the callback?
No. The callback is a browser redirect and every parameter can be forged. Use it only to learn which payment to look at, then verify.
Can I fulfil an order from the webhook?
No — the webhook is a trigger, not the source of truth, and carries no amounts. On receipt, verify the signature, dedupe, then call verify and fulfil from its response.
Why should I call verify?
Verify is the single authoritative read: it returns the real status and the money figures. It is the only signal safe to fulfil on. See Callback vs Webhook.
What happens if the customer pays too little or too much?
The USD deviation is compared against your configured tolerance: within tolerance → ACCEPTABLE (fulfil), outside → MISMATCH (review). See Amount Deviation.
What happens after a payment expires?
An unpaid payment past its timeoutSeconds deadline becomes EXPIRED (terminal). Hosted payments learn this via the webhook; there is no callback for an expiry. Do not fulfil.
What is statusOnly=true used for?
A cheap status-inquiry poll in API mode — a tiny four-field payload for driving your UI. It never flips isVerified, and you must still fulfil from verify.
Why is API Mode IP-gated?
Because the payment UUID is the only other credential on the public calls. Requiring an allowlisted server IP makes an API-mode payment invisible to anyone but your servers, even with the UUID.
How does cashout signing work?
Each request carries X-Timestamp and X-Signature = HMAC_SHA256(secret, timestamp + "." + rawBody), hex-encoded (GET signs an empty body). See Signing Requests.
Why do I need an Idempotency-Key?
So you can safely retry a settlement request without creating a second payout. Reusing the key with a different body returns 409 idempotency_conflict. See Create Settlement.