DocumentationRate limits
Ask AI

Take the docs with you

Ask ChatGPTOpen a new chat ↗Ask ClaudeOpen a new chat ↗Ask on GeminiCopy prompt, then paste in Gemini ↗View llms.txtDocumentation index ↗

External chats receive links to public docs.

Rate limits

Only endpoints that intentionally differ from the standard API carry a chip; the chip links to the note that explains the difference.

Every budget below renews on a fixed window and answers 429 when spent. Find your number in the table, check whether that 429 carries a Retry-After header, and react accordingly. A 402 is never a rate limit — it means your balance is empty, so top up instead of retrying.

/v1/chat/completions/api/dashboard/playground/chat/api/dashboard/login

Your budgets at a glance

SurfaceLimitScopeWhen exceeded
Inference (OpenAI + Anthropic)Your key's rate_limit per minute (default 500; explicit 1..1000, anything else 400)Per account — all keys combined429, no Retry-After; back off or ask support to raise it
Playground chat (dashboard session)20 requests/minPer signed-in user429, no Retry-After
Concurrent requests at low balanceUp to $0.05: 1 in flight; up to $0.25: 3; above $0.25: unboundedPer account429, no Retry-After; let requests finish or top up
Free-model fair-use (atmo/* promo)100M lifetime tokens per account; $1 lifetime deposits to unlock (both admin-configurable)Per account429 naming the remedy; paid models unaffected
Sign-in + password step-up20 tries per IP + 8 per account per 15 min; 15-min lockoutPer IP and per account429 with Retry-After; wait the stated seconds
Signup email sends3 per email/hour; 20 per IP/hour; 90 global/day; 2700 global/month; 1-min resend cooldown (defaults)Per email / IP / global429 code rate_limited with Retry-After + retry_after_seconds
Signup completion30 per IP/hour; 120 global/hour (defaults)Per IP / globalSame 429 shape as email sends
Provider webhooks30/min per IP on every callbackPer client IP429 with Retry-After

Your inference budget belongs to your account, not to any single key: every request counts against the owning user's per-minute window, so minting extra keys never multiplies it. Omit rate_limit when creating a key and it resolves to 500; an explicit value must be between 1 and 1000 — anything else (including 0 and negatives) is rejected with 400. The catalogue read (GET /v1/models) carries no per-minute budget.

What a 429 looks like

Inference refusals quote your account's own limit back at you. On the OpenAI surface:

json
{
  "error": {
    "message": "rate limit exceeded: 500 requests/min for your account (all keys combined) — wait a minute or contact support to raise it",
    "type": "rate_limit_exceeded"
  }
}

The Anthropic surface carries the same message in its own envelope:

json
{
  "type": "error",
  "error": {
    "type": "rate_limit_error",
    "message": "rate limit exceeded: 500 requests/min for your account (all keys combined) — wait a minute or contact support to raise it"
  }
}

Playground refusals are shorter (rate limit exceeded with type rate_limit_exceeded), and tired-balance refusals say too many concurrent requests for current balance — wait for in-flight requests to complete or top up. Free-model refusals carry the promo message with type rate_limit_exceeded and code free_tier_quota_exceeded on the OpenAI surface (rate_limit_error on Anthropic). Signup refusals use code rate_limited.

Who answers 429Retry-After?Body signal
Inference, playground, low-balance concurrency, free-model quota, upstream passthroughNo — back off exponentiallyOpenAI envelope (Anthropic envelope on /v1/messages)
Sign-in, password step-up, account-deletion confirmYes — wait the stated seconds{"error": "..."} string plus the header
Signup register / resend / completeYes, plus retry_after_seconds in the body{"error": {"code": "rate_limited", ...}}
Provider webhooks (sumopod, epusdt)Yes — wait the stated seconds{"error": "too many webhook calls"}
We send no X-RateLimit-* headers. The 429 itself — plus Retry-After where the table above says so — is the only rate signal.

Staying under

Honor Retry-After wherever it is present; otherwise back off exponentially — the full retry pattern lives under Errors and is not repeated here. Keep concurrent requests serialized while your balance is thin, or top up past $0.25 to lift the concurrency cap entirely. Paid models are never gated by the free-model quota: a free-model 429 names its own remedy in the message.

Retry only what is transient. Retry 429, 502 and 503 with exponential backoff. 402 means your balance is empty, so top up instead of retrying. Never retry 400, 401, 403 or 404.
Inference, playground, sign-in and webhook budgets are counted in memory per gateway process: a restart clears them, and replicas do not share them. Signup email quotas live in the database and survive restarts. Signup quota defaults shown here are operator-configurable via environment.

Where these numbers come from

These are the live gateway defaults; if one changes, this page changes with it.

Number
Sliding 1-min window; legacy limits ≤ 0 fall back to the 500 default
500 default on omit; explicit 1..1000, anything else → 400
Per-user enforcement (all keys combined)
Playground 20/min
Concurrency 1 / 3 / unbounded
Sign-in 20 + 8, 15-min window + lockout
Retry-After senders (auth, signup, webhooks)
Signup quotas + 429 shape
Free-model quota + refusal shape
Upstream 429 passthrough