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

# Sandbox mode

> Build and test the full OEM provisioning + usage + statement flow with a test-mode key — no billing, no live tenants touched.

Sandbox mode lets you exercise the entire OEM Partner API — provisioning, usage
reads, statements, lifecycle, keys, entitlement, branding — against isolated
sandbox sub-tenants that are excluded from royalty metering, wholesale rating,
and Stripe billing. It mirrors the Plaid / Stripe test-mode pattern.

## Test-mode keys

Your provisioning key carries a **mode**. Mint a **test** key for sandbox work
and a **live** key for production. The two are strictly isolated:

| A **test** key…                                        | A **live** key…                |
| ------------------------------------------------------ | ------------------------------ |
| creates sub-tenants **only** as sandbox (auto-flagged) | creates only live sub-tenants  |
| sees / manages **only** sandbox tenants                | never sees a sandbox tenant    |
| can call `simulate-usage`                              | cannot (`403 sandbox_only`)    |
| is bounded by the sandbox tenant cap (default 10)      | bounded by the live tenant cap |

Every `GET`/`PATCH`/`DELETE` is mode-scoped, so a test key can never read or
mutate a live tenant (and vice-versa) — it returns `404` as if the id did not
exist.

## Simulating usage

Generate synthetic governed events so the usage and statement flows have data
to reconcile against:

```http theme={null}
POST /tenants/{id}/simulate-usage
{ "events": 250000 }
```

Test mode only (a live key gets `403 sandbox_only`). Events are inserted as
sandbox-origin audit rows (`1..100000` per call), then immediately readable via
`GET /tenants/{id}/usage` and `GET /usage`. A closed sandbox tenant returns
`409 tenant_closed`.

## A typical sandbox run

<Steps>
  <Step title="Create a sandbox tenant">
    `POST /tenants` with a test key → `isSandbox: true`, plus a `vq_prod_…` harness
    key for that sandbox tenant.
  </Step>

  <Step title="Generate usage">
    `POST /tenants/{id}/simulate-usage { "events": 1000000 }`.
  </Step>

  <Step title="Read it back">
    `GET /tenants/{id}/usage?period=<this-month>` and `GET /usage` — confirm the
    counts and `listValueCents`.
  </Step>

  <Step title="Offboard">
    `PATCH /tenants/{id} { "action": "close" }`, then
    `GET /tenants/{id}/export` to pull the evidence stream.
  </Step>
</Steps>

Sandbox tenants are never billed and never appear in live usage, statements, or
webhooks.
