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

# Rate limits and quotas

The API enforces per-key request rates, per-account session concurrency, and monthly plan allowances. `GET /v1/usage` returns the limits that apply to your account and key.

## Request throttles

Throttles are counted per API key across every server. Honour `Retry-After` on any 429. Some capacity refusals carry a plain-string `detail` rather than a structured error.

| Bucket | What it counts | Your limit | 429 `error` |
| - | - | - | - |
| drive | Every call that drives or reads a session's browser: navigate, fetch, extract, inspect, scrape, crawl, search, task, solve, act, screenshot, elements, tabs, files, context, rotate-ip, agent, template, and the noVNC page. | `rate_limits.drive_per_minute` in `GET /v1/usage`. It scales with your concurrency cap (4 calls per minute per concurrent session allowed, with a floor every key gets). | `rate_limited` |
| session-create | `POST /v1/session`, and attempts on `POST /v1/credits/redeem`. | `rate_limits.session_creates_per_minute`. | `rate_limited` |
| inspect | Concurrent `POST /v1/inspect` captures. | `rate_limits.concurrent_inspects`: 3, whatever the plan. | `too_many_concurrent_inspects` |
| auth failures | Requests that fail authentication. | Retrying a rejected key within a minute can answer 429. Repeated failures also throttle the client address. Requests with a valid key from the same address are not affected. | plain string |

A `rate_limited` answer carries these fields in `detail`: `error`, `message`, `limit`, `window_seconds` (60), `scope` (`api_key`) and `retry_after_seconds`, with the headers `Retry-After`, `X-RateLimit-Limit`, `X-RateLimit-Remaining: 0` and `X-RateLimit-Reset` (a Unix timestamp).

The inspect cap, as returned when a fourth capture is started:

```
HTTP/1.1 429
Retry-After: 5
X-RateLimit-Limit: 3
X-RateLimit-Remaining: 0
```

```json theme={"dark"}
{
  "detail": {
    "error": "too_many_concurrent_inspects",
    "message": "too many concurrent inspect captures: 3 at a time for this API key, counted across all workers; retry in 5 s",
    "limit": 3,
    "scope": "api_key",
    "retry_after_seconds": 5
  }
}
```

The auth throttle answers 429 with `{"detail": "invalid API key; too many failed attempts from this address, retry later"}` and a `Retry-After` header.

## Concurrency

Concurrency counts live sessions across your whole account, not requests, and the cap is `concurrency_limit` in `GET /v1/usage`. A create past the cap answers 429 with `detail` fields `error: "concurrency_limit"`, `message`, `limit`, `tier` and `upgrade_url`. The usual cause is sessions that were never released: list them with `GET /v1/sessions`, keep `idle_timeout` short, and release in a `finally` block.

Tabs are capped per session as well. `GET /v1/session/{id}/tabs` reports your session's `max`; opening one more answers 429 with `error: "tab_limit"` and `limit` in `detail`.

## Plans and the monthly allowance

| Plan | Concurrent sessions | Browser hours per month | Premium egress included | Longest session | Past the allowance |
| - | - | - | - | - | - |
| Free | 10 | 10 | 1 GB | 30 min | hard stop |
| Developer | 25 | 250 | 2 GB | 2 h | metered overage |
| Team | 250 | 2500 | 25 GB | 12 h | metered overage |
| Pro (earlier plan) | 50 | 500 | 10 GB (and 10,000 actions, 15,000 solves) | 6 h | metered overage |
| Scale (earlier plan) | 200 | 5000 | 35 GB (and 100,000 actions, 50,000 solves) | 12 h | metered overage |
| Enterprise | 250 and up | unlimited | negotiated | unlimited | metered |

Browser hours, concurrency and premium egress (traffic through residential, ISP and mobile exits) are the metered axes on the current plans; actions and CAPTCHA solves are uncapped there. Developer and Team are card billed without per-call wallet debits. Self-healing is on every plan; the paid-exit traffic it spends is premium egress. A plan past its allowance without overage (Free) is refused with 402 `quota_exceeded` or `premium_egress_exhausted`; paid plans continue and the excess is invoiced.

`null` in `limits` or `remaining` means unlimited on your plan. Only the default `ttl` is lowered to the plan's longest session. An explicit larger value answers 422 `ttl_exceeds_plan` with `max_ttl`. The request accepts values from 5 to 604800 seconds, subject to that plan limit.

## Body size and deadlines

* A request body over 4 MB answers 413 `{"detail": "request body too large"}`.
* Most synchronous `/v1` calls have a server-side deadline of about 57 seconds. Past it the API answers 504 `{"error": "deadline_exceeded", "detail": "...", "deadline_s": 57}` with `retry_with: "async_mode"`, the session intact. Session creation has a separate wait budget. Fetch, extract, inspect, search, solve and agent take `async_mode: true` to run as a job you poll on `GET /v1/job/{id}`; fetch also takes `on_deadline: "continue"`.
* An inspect capture is capped at 180 seconds plus a fixed overhead for the page load and the report.


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