Limits
Your limits depend on your plans and apply to your whole account, across all your keys. Track your usage at any time with GET /v1/usage.
Limits by plan
Live and Historical stack: with both, you get the rights of both. With Live alone, an fc_live_ key has no access to history, not even the Sandbox’s 7 days. A test key always keeps the Sandbox rights. What each plan includes and how to buy it: Plans and billing.
| Limit | Sandbox | Live | Historical | Live + Historical |
|---|---|---|---|---|
| Billing | Free | Monthly subscription | One-time purchase, lifetime access | Monthly subscription + One-time purchase, lifetime access |
| Stream | 10-minute delay | Real time | 10-minute delay | Real time |
| Concurrent connections | 1 | 5 | 1 | 5 |
| Concurrent subscriptions | 2 | 50 | 2 | 50 |
| Custom configurations | 1 | 25 | 1 | 25 |
| History | Last 7 days | Not included | Full available depth | Full available depth |
| Monthly compute budget | 50,000,000 units | Not included | 20,000,000,000 units | 20,000,000,000 units |
| Monthly export volume | Not included | Not included | 20 GiB | 20 GiB |
| REST requests, all keys together | 60 per minute | 300 per minute | 1,200 per minute | 1,200 per minute |
How limits are counted
- Per account: connections, subscriptions, budgets and REST requests per minute are shared by all your keys. Creating more keys does not raise your limits.
- Custom configurations: a WebSocket subscription whose parameters differ from the indicator’s defaults, display parameters included (
category: "view"in the catalog). For example, Fathom Trades with a minimum volume (minimum) of 50 instead of 30. Each combination of contract, indicator and parameters counts once, even if several subscriptions use it:liveandconfirmedcount once, andNQ.frontcounts as the contract it designates (NQ.frontandNQZ6with the same parameters: one configuration). A configuration is released when the last subscription using it closes (unsubscribeor the connection closing; a connection lost without a close is closed by the server after 30 seconds of silence, or released after about 90 seconds at most if our server stops). History queries and exports use none. - Compute budget: every access to history (a query, an export, or a subscription that starts in the past) consumes compute units: the number of trades in the requested range (
trades), multiplied by the indicator’s cost per trade (computeUnitsPerTradein the catalog, currently 1 for every indicator). The Sandbox’s 50 million compute units cover about 50 to 165 trading days at 1 compute unit per trade. The details are in What drives the cost. Estimate that cost before every query, for free. A live subscription (from: "live") consumes nothing; of afrom: {"time": …}subscription, only the part before midnight UTC today is charged, page by page as it is sent. - Exports: the compute cost of an export’s whole range is charged as soon as it starts, even if you stop reading the response before the end; a resume within 24 hours costs no compute units (see Exports).
- Export volume: the amount of data your exports download, compressed, as you receive it, charged at the end of every response, resumes included.
The compute budget and the export volume renew at the start of every month (UTC), including with the lifetime access of the Historical plan. A request that would exceed them is rejected before it starts, with 429 QUOTA_EXCEEDED.
Technical limits
Unless stated otherwise, these are the same for every plan.
| Item | Limit | If you exceed it |
|---|---|---|
| REST requests | Depends on your plan, per minute, all the account’s keys together | 429 RATE_LIMITED |
| REST request body size | 16 KiB (16,384 bytes) | 413 |
Valid keys (active or expiring) | 10 per account | 409 QUOTA_EXCEEDED |
| Allowed instruments and IP addresses per key | 32 of each | 400 INVALID_PARAMETERS |
| Grace period when rotating a key | 7 days at most | 400 INVALID_PARAMETERS |
| Sign-in links | 5 per hour per e-mail address, valid for 15 minutes | 429 RATE_LIMITED |
| Browser stream token | Valid for 60 s, single use | Connection closed (4001) |
auth message after the WebSocket opens | 5 s | Connection closed (4001) |
| Message sent on the WebSocket | 64 KiB (65,536 bytes), fragments included | Connection closed (1009) |
| Messages sent by your client on the WebSocket | 20 per second on average, bursts of 100 (control frames included) | Connection closed (1008) |
Subscription name (sub) | 1 to 64 characters (an accented character counts as two), unique on the connection | error INVALID_PARAMETERS |
| Resume from a cursor | About the last 15 minutes of updates (less in a very busy market); no age limit on a stream that published nothing since your cursor; beyond, caught up from history when your rights cover the cursor’s UTC day, charged like a from: {"time": …} | reset (cursor_expired), then a new snapshot |
| Data waiting to be sent (slow client) | 256 KiB, then 1 MiB | Intermediate versions skipped, then connection closed (4008 SLOW_CONSUMER) |
| Client silence | 30 s | Connection closed (4008 PING_TIMEOUT) |
| Results per history page | 1 to 10,000 (1,000 by default), within a bounded page size (about 5,400 footprint bars) | Next page through next |
Requests per minute
Your account can send a set number of REST requests per minute, depending on your plan, all keys together. This allowance refills continuously, up to that limit. Every response to a request whose key is recognized carries these headers, a 403 for a missing scope included, as well as a 404 or 405 on an unknown path or method (these requests count toward the limit too). A 401 (missing, invalid, revoked or expired key) belongs to no account and carries none of them, and neither do the public routes, which do not read the key (/v1/indicators, /v1/offers, /v1/pricing):
RateLimit-Limit: 1200
RateLimit-Remaining: 1197
RateLimit-Reset: 1
RateLimit-Policy: 1200;w=60RateLimit-Remaining: requests available right now;RateLimit-Reset: seconds until the full limit is restored;RateLimit-Policy: the limit and its window, in seconds.
Past the limit, the request is rejected with 429 RATE_LIMITED; the Retry-After header says how many seconds to wait. The SDK waits and retries automatically.
Track your usage
curl https://api.fathomcharts.com/v1/usage -H "Authorization: Bearer $FATHOM_CHARTS_API_KEY"{
"period": "2026-10",
"resetsAt": "1793491200000000000",
"plan": "live_history",
"limits": {
"computeBudget": 20000000000,
"exportBytes": 21474836480,
"restPerMinute": 1200,
"historyDays": 36500,
"delaySeconds": 0,
"maxConnections": 5,
"maxSubscriptions": 50,
"maxCustomConfigs": 25,
"realtime": true
},
"used": { "computeUnits": 1840233, "historyItems": 51207, "exportBytes": 734003200, "restRequests": 412 },
"remaining": { "computeUnits": 19998159767, "exportBytes": 20740833280 }
}plan: your plans, one ofsandbox,live,historyorlive_history(both);periodandresetsAt: the current month and the date of the next renewal;limits: the limits that apply to you. With a test key, these are the Sandbox limits.historyDaysis 0 without history (Live plan alone), 7 on the Sandbox, and 36500 for all of our history;usedandremaining: your usage this month and what you have left.historyItemscounts the results your historical queries received,restRequestsyour REST requests.