> ## Documentation Index
> Fetch the complete documentation index at: https://docs.brand-wallet.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Roll back a transaction

> Undo a committed transaction: collected stamps/points are restored, granted reward coupons are cancelled, and a redeemed coupon becomes active again.

```http theme={null}
POST $BASE_URL/v1/transactions/:transactionId/rollback
```

**Undoes a committed transaction — use it for cancelled orders and cashier mistakes. Collected stamps/points are restored to their pre-transaction values, reward coupons granted by the transaction are cancelled, a coupon redeemed by the transaction becomes active again, and promotion usages are reverted. The transaction id is the `transactionId` returned by [process](/api/process-transaction).**

> **Auth:** `Authorization: Bearer <accessToken>` — an organization-scoped token from [Authentication](/api/authentication). A transaction that does not exist or belongs to another organization returns `403 auth_error`.

What is undone depends on what the transaction did:

* **Stamp / point collection** — the card's balances return to their pre-transaction values; reward coupons granted by the transaction are cancelled.
* **Discount / membership** — the usage counters are reverted. The monetary refund itself happens on your side (the discount was applied at your register).
* **Coupon redemption** (`redeem-coupon` transactions) — the redeemed coupon becomes active again and can be redeemed later.

### Rules

* **Latest-transaction rule:** for collection transactions (stamps, points, discounts, membership), only the **most recent** non-rolled-back transaction of that customer + campaign can be rolled back; an older one fails with `400 transaction_is_not_latest`. To undo several, roll them back in **reverse order** (newest first). `redeem-coupon` transactions are exempt from this rule.
* **Used-reward guard:** if a reward coupon granted by the transaction has already been redeemed by the customer, the rollback fails with `400 reward_coupon_already_used` and **nothing is changed** (there is no partial rollback).
* **No repeat:** a rolled-back transaction cannot be rolled back again — `400 transaction_already_rolledback`. Treat that response as "already undone".

### Body

| Field | Type | Description |
| - | - | - |
| `reason` | string | Optional cancellation reason — stored on the transaction as `rollbackReason` and visible in [list](/api/list-transactions)/[get](/api/get-transaction). |

### Example

```bash theme={null}
curl --request POST \
  --url "$BASE_URL/v1/transactions/7f1b6c20-8f2e-40d7-966f-29707f1a77b9/rollback" \
  --header 'Authorization: Bearer <accessToken>' \
  --header 'Content-Type: application/json' \
  --data '{ "reason": "cashier cancellation" }'
```

### Response

```json theme={null}
{
  "transactionId": "7f1b6c20-8f2e-40d7-966f-29707f1a77b9",
  "rolledBack": true
}
```

Error example:

```json theme={null}
{
  "statuscode": 400,
  "errorcode": 400,
  "message": "transaction_already_rolledback",
  "description": "upstream status 400",
  "timestamp": 1791455874000,
  "path": "/v1/transactions/7f1b6c20-8f2e-40d7-966f-29707f1a77b9/rollback",
  "method": "POST"
}
```

Notes:

* Possible **400** errors: `transaction_already_rolledback`, `transaction_is_not_latest`, `reward_coupon_already_used`, `reward_coupon_not_found`, `redeem_coupon_not_found`, `coupon_is_not_redeemed` (the coupon of a `redeem-coupon` transaction is no longer in redeemed state), `rollback_not_supported_for_external_transaction` (the transaction came from an external integration), `rollback_not_supported_for_system_transaction` (a system correction transaction), `rollback_not_supported_for_legacy_transaction` (an old record without a pre-transaction snapshot), `rollback_exceeds_current_threshold` (the campaign's threshold changed and the restored value would exceed it).
* A reward coupon granted at a threshold crossing is cancelled by the rollback, and the balance returns to its pre-threshold value — the customer can earn the same reward again.
* When a single process call ran more than one campaign, it returns `transactionIds` — roll them back in **reverse** order.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.