Sandbox Testing
Test keys never touch real money. Drive any payment outcome on demand with the sandbox simulator, so your integration handles success, failure and timeouts before you go live.
Test keys only
The simulator is only available with
pk_test_… / sk_test_… keys. Live transactions are settled by the real provider rails and cannot be simulated.Simulate a transaction
Create a transaction as usual (checkout, collection or payout), then push it through any scenario with the simulate endpoint. The transaction transitions exactly as it would in production — including firing the matching webhooks to your test-environment endpoint.
POST
/api/v1/merchant/sandbox/simulateForce a sandbox transaction into a specific outcome.
Authenticates with your API keys.
Body parameters
| Parameter | Description | |
|---|---|---|
reference | required | stringThe reference of the transaction to simulate. |
scenario | required | stringOne of collection.success, collection.failed, payout.completed, payout.failed, timeout. |
curl -X POST "https://api.namibrapay.com/api/v1/merchant/sandbox/simulate" \
-H "X-API-Key: pk_test_xxxxxxxxxxxxxxxx" \
-H "X-API-Secret: sk_test_xxxxxxxxxxxxxxxx" \
-H "Content-Type: application/json" \
-d '{
"reference": "ORDER-12345",
"scenario": "collection.success"
}'200
{
"success": true,
"data": {
"reference": "NPR-8fj29dk1",
"status": "success",
"amount": 2500,
"currency": "GHS",
"channel": "mtn_momo"
},
"message": "Scenario 'collection.success' applied"
}Scenarios
| Scenario | What happens |
|---|---|
| collection.success | The collection is marked successful and settles to your test balance. |
| collection.failed | The provider declines the charge; the transaction ends as failed. |
| payout.completed | The payout completes and debits your test balance. |
| payout.failed | The payout is rejected by the rail; funds return to your balance. |
| timeout | The provider never responds — the transaction stays pending until reconciliation. |
Tips for testing
- Always test the
timeoutpath — reconciliation may later resolve a stale transaction, and your code must handle the latecollection.successwebhook. - Verify idempotency: send the same
referencetwice and confirm your side doesn't double-charge. - Point a public webhook URL (e.g. via ngrok) at your local server to watch real event deliveries in test mode.
- Check Webhooks → Logs in the dashboard (or the
webhooks/logsendpoint) to inspect every delivery, response and retry.