//Windowed Scope Re-mint API

Windowed Scope Re-mint API

Just-in-time / step-up scope acquisition. When your app navigates into a sensitive context, ask ButtrBase for a fresh access token that carries only that context's scopes (least-privilege "windowed" strategy). The granted set is always a subset of the caller's effective scopes, and each requested scope is run through the scope-gate (step-up) machinery.

Endpoint

POST /api/app/auth/scope-context

Re-mint an access token windowed to an explicit, gate-checked scope subset.

Auth: requires a valid access token (Authorization: Bearer <access JWT>).

Input: ~~~json { "requested_scopes": ["billing:read", "billing:write"] } ~~~

Output (200): ~~~json { "token": "", "scopes": ["billing:read", "billing:write"] } ~~~

scopes is the granted (sorted, de-duped) set — identical to the data.scopes claim embedded in the new token. Only the access token is re-minted; your refresh token is unchanged.

Error responses

  • 403 { "error": "forbidden", "scope": "" } — you do not hold the
  • scope, or a gate forbids it.
  • 401 { "error": "step_up_required", "scope": "", "factor": "" }
  • — a gate requires a fresh step-up factor (e.g. webauthn, totp) that your current token does not carry within the gate's freshness window. Complete the step-up and retry.
  • 500 — the endpoint fails closed: on any scope/gate resolution
  • uncertainty it returns 500 and never mints a (potentially over-privileged) token.

    Scope strategies

    Set per-tenant in your token policy:

  • accumulate — tokens minted at login/refresh embed your full effective
  • scope set.
  • windowed* — login/refresh tokens embed your effective set *minus any
scope whose gate requires a factor; gated/sensitive scopes only enter a token via this endpoint, never the baseline.