Pricing & quotas
Every scrape spends credits from a monthly pool tied to your plan. Each plan also caps how many scrapes you can run at once. Both limits are enforced on the /scrape (and /map) hot path.
Credit cost per engine
Section titled “Credit cost per engine”Cost is charged per URL, keyed by the engine you request (a multi-URL request costs the sum). The weights track real infrastructure cost — a plain fetch is the floor, an AI exploration pass adds model tokens, and a Chromium session is the expensive part.
| Engine | Credits / URL |
|---|---|
html | 1 |
ai-html | 3 |
browser | 5 |
ai | 5 |
ai-browser | 10 |
ai auto-resolves to the html or browser runner at request time, but that’s unknown when we charge, so it’s priced at the browser tier — it’s not a cheap path to a browser run. Caching a generated AI plan and POSTing it back as deterministic actions drops the per-run cost to the underlying engine’s rate (1 or 5).
credits is the monthly pool (reset at the start of each UTC month, no rollover); concurrency caps simultaneous in-flight scrapes per user. New accounts start on free.
| Plan | Price / mo | Monthly credits | Concurrency |
|---|---|---|---|
free | $0 | 1,000 | 2 |
starter | $49 | 25,000 | 5 |
growth | $149 | 150,000 | 15 |
scale | $499 | 750,000 | 40 |
Manage your subscription on the billing page. The same catalog is available programmatically at GET /billing/plans.
Checking usage
Section titled “Checking usage”GET /usage (Clerk-authenticated, like the rest of /me/*) returns the current period’s quota state:
{ plan: 'free' | 'starter' | 'growth' | 'scale'; period: string; // UTC "YYYY-MM" creditsLimit: number; creditsUsed: number; creditsRemaining: number; concurrencyLimit: number;}The dashboard’s billing page is a visual wrapper over this.
Hitting a limit
Section titled “Hitting a limit”| Status | Body | Cause |
|---|---|---|
402 | { "error": "credit quota exceeded", "creditsLimit", "creditsUsed", "creditsRemaining": 0 } | The request would exceed your monthly credit pool. Upgrade your plan or wait for the next period. |
429 | { "error": "concurrency limit exceeded", "concurrencyLimit" } | Too many scrapes already in flight for your account. A Retry-After: 5 header is set — back off and retry. |