# API keys

Request your first key with the **Apply for API Access** form, then scope, rotate and revoke keys from **Settings → API keys**.

## Creating a key

1. Request access with the **Apply for API Access** form
2. Name it after where it runs (`prod-web`, `etl-worker`) — not after a person
3. Choose a scope preset: **Full access**, **Read only**, or **Custom**
4. Optionally set a monthly credit cap for this key
5. Copy the value

> [!warning] Shown once
> The full key appears only at creation. Afterwards you see `sk_live_7f3a…5c1f`. Lost keys are
> replaced, not recovered.

## Scope presets

| Preset | Grants |
|---|---|
| Full access | every scope except `webhooks:write` and `usage:read` |
| Read only | all `*:read` scopes |
| Custom | exactly what you select |

> [!warning] Grant the minimum
> Select only the scopes a key needs and delete keys you no longer use. Prefer one key per
> deployment so revoking one does not take down everything.

## Per-key credit caps

A key can carry a monthly credit ceiling. When it is reached the key returns `402
insufficient_credits` while other keys keep working — the practical way to stop a runaway job from
consuming the whole organization's balance. See teams-and-scopes.

## Rotation

1. Create the replacement key with identical scopes
2. Deploy it
3. Confirm traffic has moved in usage (`group_by=api_key`)
4. Revoke the old key

Keys never expire on their own, and overlapping keys are supported, so rotation needs no downtime.

## Revocation

Revoking takes effect within 60 seconds across all regions. In-flight async jobs created by a revoked
key continue to completion, and their results stay readable by any key with the matching read scope.

## Storage rules

- Secret manager or environment variables only
- Never in source control, client bundles, CI logs, or error reports
- Rotate immediately on suspected exposure, then check usage for unexpected consumption

## Related

authentication · teams-and-scopes · usage · pricing-and-credits
