What can and cannot be simulated? Give me the whole list.
Everything in the “No” rows is genuinely absent rather than undocumented, so plan
around it: prove those code paths with unit tests against recorded payloads, and
verify the live behaviour in production once you are live.
Which reserved amounts trigger which error, and on which endpoints?
The sandbox intercepts specific order amounts and returns the matching error instead of processing normally. The mapping:
Read the “applies to” column carefully, because it is where the mistakes happen:
- On create, the amount is taken from the request — the order amount on an order create, the amount on a subscription create.
- On cancel, you do not pass an amount. The amount matched is the one stored
on the order or subscription you are cancelling. So to test a cancel error you
must create the order at
9.3first, then cancel it. - These amounts are a sandbox-only rule. Nothing like this exists in production, where the same amounts are ordinary amounts.
Why do the reserved refund amounts not work?
Because the refund path does not use the refund-specific amounts. The9.5 and
9.6 families listed for the refund API on the published
Sandbox simulator
page do not take effect — a refund of 995 is an ordinary refund.
What the refund path does react to are the create families: a
refundAmount equal to one of the 90 / 9.1 / 9.2 family values (the same
amounts that trigger C0005, C0001 and E0001 on order create) makes the
refund request fail at request time with an error of the matching class — a
channel or system error for the 90 and 9.1 families, an unknown-status error
for the 9.2 family. The refund order that was opened for the request finishes
as REFUND_FAILED, and a refund notification reporting the failure is sent to
your refund notify URL. That lets you prove your handling of a rejected refund
request and of a failed refund record; what it cannot give you is a refund that
first goes in progress and fails later, and there is no other way to force one in
the sandbox. What you can still prove on the refund path:
For a genuine refund failure, test your handler against a recorded payload
rather than trying to provoke one.
My real prices land on the reserved amounts and my sandbox orders keep failing
This is a known situation and it has a fix that is not “change your prices”: a sandbox merchant ID can be exempted from amount simulation. Contact integration support with your sandbox merchant ID and ask for the exemption; once applied, reserved amounts behave as ordinary amounts for your sandbox. Until then, the workaround is to avoid the five families above. In practice that means avoiding amounts ending in90, and the 9.x / x91–x96 patterns —
adding a cent (for example 90.01 instead of 90) is enough, because the match
is exact.
Does the sandbox really send webhooks?
Yes. Sandbox webhook delivery follows the same contract as production — the same signature, the same accepted response body, the same retry schedule. Everything in Webhook Delivery Contract FAQ applies unchanged. Two things that are not different but get blamed for looking different:- Your
notifyUrlmust be publicly reachable. The sandbox cannot reachlocalhostor a private address, and your TLS certificate must be publicly trusted. Use a tunnelling tool for local development. - Perceived sandbox delay is usually the retry schedule. If a first delivery fails, the next attempts follow a growing back-off — see Webhook retry for the schedule. A notification that “took minutes to arrive” almost always means the first attempts were rejected — check the Portal webhook log for the earlier failed attempts on the same record before concluding the sandbox is slow.
Which test card numbers should I use?
Use the quick-fill buttons on the sandbox checkout page when a flow asks you to enter a card. They populate the card number, an expiry and a CVV for a success or a decline in one click, per card brand, for the brands your sandbox has enabled — which removes both the transcription errors and the guesswork about which value that environment expects. If you need the values written down, the Portal’s own list is at Merchant Portal → Integration → Test Cards, with a copy action per card and two scenario categories: successful and failed. The table in Sandbox Testing FAQ matches the Portal list. The older published simulator page does not agree for every scheme, so prefer the in-product source over any document, and prefer the checkout quick-fill over both.What do I enter for expiry and CVV? Are they validated?
Any future expiry date, and any CVV of the right length — three digits, four for the schemes that use four. The quick-fill on the checkout page supplies a valid combination for you. What this tells you about coverage: because expiry and CVV are not meaningfully validated, the sandbox cannot prove your handling of an expiry-date rejection or a CVV mismatch. Those belong to the “test against a recorded payload” list.The Portal test card page shows only success and failure. Where are the 3DS, insufficient-funds, CVC-error and risk-decline cards?
They do not exist. The Portal test card list has exactly two scenario categories, successful and failed, and there is no card number that maps to a specific decline reason. The consequence for acceptance planning: the sandbox proves that your code takes the right branch on success and on failure. It does not let you enumerate decline reasons. Where your product behaves differently per decline reason — a retry prompt for insufficient funds versus a “use another card” prompt for a hard decline — drive those branches fromorderFailedReason in unit tests, using the
codes in
Error codes.
How do I simulate a renewal, and can I chain periods?
From the subscription management page, which you obtain by callingPOST /api/v1/subscription/manage and opening the returned managementUrl. It
offers a simulated successful next payment and a simulated failed next payment,
and each click advances one period — so you can chain them: period 2 succeeds,
period 3 fails.
Preconditions, because these are what make the buttons unavailable:
If the page renders but the simulation controls are absent, check the
subscription’s status first — an unactivated or already-cancelled subscription is
by far the most common cause.
Will a simulated failed period then retry on the normal schedule?
No — and this is the most important thing on this page. Simulating a failed renewal sets the renewal retry allowance to zero first, so the failed period goes straight to its terminal state instead of entering the retry schedule. Two consequences to plan around:- You cannot observe renewal retry behaviour in the sandbox by simulating a failure. The retry schedule that runs in production is bypassed by the simulation itself.
- The change persists for that sandbox subscription’s configuration. Renewal retries stay disabled afterwards, so a subscription you used to simulate a failure is no longer a clean subject for retry testing. Create a fresh subscription for anything retry-related.
Can I simulate the customer cancelling inside their wallet app?
Yes, for the payment methods where it is supported. The simulation produces the sameSUBSCRIPTION_STATUS_NOTIFICATION with USER_CANCELLED that a real
customer-side cancellation produces, so your handler sees the real thing.
Two gates decide whether it works for a given subscription:
- The subscription must be
ACTIVE. - The payment method must support it. Wallet-side cancellation is simulated by reproducing the message that payment method actually sends on cancellation, so it exists only for methods where that message is modelled. Where it is not, the call fails with a dedicated “this payment method does not support channel cancel” error rather than silently doing nothing — which is itself the answer to whether your method is covered: try it and read the error.
USER_CANCELLED payload. The notification shape does not vary by payment method.
Can I test a chargeback in the sandbox?
No. There is no chargeback or dispute simulation in the sandbox — no reserved amount, no button, no endpoint. What to do instead:
Also worth knowing before you plan around it: the chargeback notification is only
delivered if the Chargeback Notify URL is configured in the Portal, and it is
Portal-configured only — there is no request parameter. So the first thing to
verify is that the URL is set, in both environments.
An order is stuck in an unknown state. How do I drive it to a final result?
E0001 is returned at create time by a reserved amount, and the request is
rejected before any order is created — an inquiry on that request id comes
back as “order does not exist”. That is the point: an unknown-status response
tells you nothing about whether an order exists, so the behaviour to prove is
your recovery logic — treat the result as undetermined, inquire, and act on what
the inquiry returns; never mark the order failed or close it yourself. When the
inquiry confirms nothing exists, re-submit with identical parameters (your
paymentRequestId makes that safe).
There is no sandbox control that produces an order which then sits in an
unknown state and flips to a final result later. So the behaviour to demonstrate
is the inquire-then-decide loop and the “did not self-close” property, not a
final state you produced by hand. The acceptance criteria phrase this as: do not
close the order, retry with identical parameters, and wait for the inquiry result
or the notification. See
Integration acceptance criteria.
Do I need a network exit in a particular country to test?
Not for the sandbox. Nothing in the sandbox payment path checks where your request or your browser comes from, and because the sandbox does not connect to real payment channels there is no channel-side geographic restriction to satisfy either. A sandbox run from anywhere is a valid sandbox run. Where geography does matter is production verification of methods that genuinely depend on the customer’s region — device or account region settings for the mobile wallet products, and the supported-country lists those products publish. Those checks are listed in Sandbox and testing under the per-payment-method sections, and they are production checks, not sandbox ones.Which things can only be verified in production?
Keep this list next to your go-live plan, because each item is a place where a green sandbox run proves nothing:
The mobile wallet checks in particular have their own prerequisite lists —
accounts, cards, device regions, in-app browser configuration, and a production
access request that must be approved before launch. Work through
Sandbox and testing and
Payment method integration notes
rather than discovering them at cutover.
Do I have to test every contracted payment method individually?
No. The acceptance criteria set out representative coverage rather than exhaustive coverage: at least one card, at least one per country per type, at least one virtual account, every method with special required parameters, and manual device testing for the mobile wallets. The full rule set is in Integration acceptance criteria. Two follow-ups that come up constantly:- A method your agreement does not allow refunds on does not need a refund case. Run the conditional cases only for the APIs and behaviours your integration actually includes — the templates mark them as conditional for that reason.
- A second integration is not a full re-run. Once you have passed acceptance at least once, a subsequent one-time-payment integration uses the additional integration template, which covers only the delta. Your first integration always uses the standard template.
Next: Go-live checklist for the switch itself, and Sandbox Environment & Access FAQ for what does and does not carry over from the sandbox.