Seamless Wallet/rollback
Rollback
Callback · Provider → OperatorPOST{callback_url}/rollback
Boss Hub calls this endpoint so you can reverse a bet or a win: when a bet reply never arrives, when the provider cancels a transaction, or on an approved result cancellation. Even if you do not know the referenced transaction, answer OK and record it.
Headers
| Header | Description |
|---|---|
| Content-Type | application/json |
| X-Operator-Id | Your operator ID |
| X-Timestamp | Unix seconds. Reject it outside ±30 s |
| X-Signature | hex(HMAC_SHA256(secret, ts + "." + "POST" + "." + path + "." + body)). path is the full path of your callback address, base path included, e.g. /bossgaming/bet. See Signing |
| X-Request-Id | The ID of this call. Stays the same across retries |
| X-Api-Key | The API key whose secret signed the callback. Selects the right secret when you have several keys |
Unknown transaction: A bet that timed out may still be in progress on your side. If ref_transaction_id is unknown, answer OK and record it; when a bet or win with that ID arrives later, return TRANSACTION_ROLLED_BACK. Otherwise the bet is processed and the player loses their money.
Idempotency: If the same transaction_id arrives again with the same body, do not refund again; return the first response as is, not the current balance. If the ID comes with a different body, answer DUPLICATE_TRANSACTION.
Token expiry: Accept the rollback even if the player’s token or session has expired; do not answer INVALID_TOKEN.
200Transaction reversed
{
"status": "OK",
"balance": 150.60,
"currency": "USD",
"operator_tx_id": "op_tx_9921846"
}200Unknown transaction: OK, record kept
{
"status": "OK",
"balance": 150.60,
"currency": "USD"
}200Uncertain error: retried on the schedule
{
"status": "ERROR",
"code": "INTERNAL_ERROR"
}Reply rules
- Answer every call with HTTP 200; a business rule error also goes out with HTTP 200, status: ERROR and a code. Any other HTTP status (3xx, 4xx, 5xx, a WAF page) counts as uncertain. The only exception is 409 TRANSACTION_NOT_FOUND on a rollback.
- In a status: OK reply, currency is required and must equal the currency of the request. If it is missing or different, the reply counts as uncertain and an alarm is raised.
- balance: the balance after the transaction; a JSON number or a number string, at most two decimals, no exponent (1e3). Required on balance; send it on the other calls too.
- Return your own transaction ID in operator_tx_id. If you put transaction_id in the reply, it must equal the one in the request.
- A body that cannot be parsed, an unknown status, or an error without a code counts as uncertain and raises an alarm. Ignore request fields you do not recognise.
- Amounts are JSON numbers with two decimals (2.00), not strings. Read the body without loss; do not use float.
When it arrives, how to handle it
- Uncertain bet: an automatic rollback follows when bet gets no clean reply on any attempt (the first attempt + the retries you chose), when the time budget runs out, or when it answers INVALID_SIGNATURE or DUPLICATE_TRANSACTION. It is not sent until the last attempt has timed out. No rollback goes out for a bet that was never sent.
- Win reversal: ref_transaction_id can be a win. In that case you debit the amount from the balance.
- Round with a win: if a bet you answered OK belongs to a round with a paid or payable win, the bet is not refunded automatically; an item awaiting resolution opens (rollback_after_win, or rollback_after_jackpot in a round with a jackpot drop). An uncertain bet is refunded even if the round has a win. If the result is cancelled, wins go first and bets last. If a step fails, the sequence stops.
- Free round: a free round bet has amount 0, so a rollback refunds no cash. The spin used is returned to the player.
- Retries: a rollback is retried on the win schedule. The body and X-Request-Id are the same on every attempt. Ignore body fields you do not recognise.
Error codes
| Code | Meaning | Boss Hub behaviour |
|---|---|---|
| TRANSACTION_ROLLED_BACK | The transaction was already reversed | Counted as OK |
| TRANSACTION_NOT_FOUND | HTTP 409, or HTTP 200 + code. Contract violation: an unknown transaction must get OK | No retry, the round becomes stuck (rollback_rejected) |
| PLAYER_BLOCKED | Player restricted / self-exclusion | No retry, the round becomes stuck (rollback_rejected) |
| LIMIT_EXCEEDED | Responsible gaming limit exceeded | No retry, the round becomes stuck (rollback_rejected) |
| INSUFFICIENT_FUNDS | Insufficient balance (win reversal) | No retry, the round becomes stuck (rollback_rejected) |
| INVALID_TOKEN | Contract violation: a rollback is not rejected over a token | No retry, the round becomes stuck (rollback_rejected) |
| DUPLICATE_TRANSACTION | Same transaction with different content | The schedule stops, goes to manual review (duplicate_conflict) |
| INVALID_SIGNATURE | Signature could not be verified | Treated as uncertain: the schedule continues, an alarm is raised |
| INTERNAL_ERROR | Operator error | Treated as uncertain: the schedule continues |
After attempt 4, a bet_timeout item opens for a bet rollback and a rollback_rejected item for a win rollback; when the schedule ends, the item waits for manual resolution. How every reply is classified: Error codes.