Quotas and rate limits
Two kinds of limits apply:
- Daily quotas cap the requests and the response bytes per UTC day. They reset at 00:00 UTC.
- Rate limits cap requests per second and, on the free tier, concurrent calls.
Daily quotas
Section titled “Daily quotas”| Plan | Counted per | Quota per UTC day | When it runs out |
|---|---|---|---|
| Free | Client IP, and site (the host in Referer) |
128k requests or 2 GB, whichever comes first | 403, more requests dropped at random as usage nears the quota |
| Boost | Endpoint: all its tokens, sites and IPs together | 256k requests and 4 GB; reaching either one is enough | 429 with a JSON body until 00:00 UTC |
| Unlimited | – | No daily quota | – |
| Enterprise | – | No daily quota | – |
- Every request counts, including errors and rejected requests. Bytes are the size of the responses.
- Usage reaches the edges with a delay of a few minutes, so a busy client can go a little over its quota before it is stopped.
- On the free tier, IPFS gateway traffic counts toward the same quota as the APIs.
Free tier: 403
Section titled “Free tier: 403”As a client IP or a site gets close to its daily quota, the edge rejects a growing share of its requests at random. Once the quota is used up, it rejects them all until 00:00 UTC. Rejected requests get:
HTTP/2 403
Daily free API quota exceededFollow free-tier usage on the public dashboard. If your app needs a higher request rate, its own API token or analytics, the Boost plan gives an endpoint 256k requests and 4 GB a day that no one else shares. More can be added in blocks of 256k requests and 4 GB a day; steady traffic beyond that suits Unlimited.
Boost: warning header, then 429
Section titled “Boost: warning header, then 429”From 80 % of either quota, responses carry an X-And-Quota header and the portal sends you an email. At 100 % of either quota, the edge answers every request of the endpoint with a 429 until 00:00 UTC, and the portal emails you again:
HTTP/2 429content-type: application/jsonretry-after: 20117x-and-quota: block=1;reqs=256154;bytes=3200000000;ts=2026-11-02
{"message":"Daily Boost quota exceeded","ld":"acme","requests":256154,"bytes":3200000000,"day":"2026-11-02","reset_in":20117}| Field | Meaning |
|---|---|
message |
Always “Daily Boost quota exceeded” |
ld |
Your endpoint’s log name, as shown in the portal analytics |
requests, bytes |
The endpoint’s usage today |
day |
The UTC day the quota is counted for |
reset_in |
Seconds until 00:00 UTC, the same as Retry-After |
X-And-Quota has the form block=<0|1>;reqs=<requests today>;bytes=<bytes today>;ts=<UTC day>. block=0 is the warning from 80 %; block=1 means the quota is used up.
Retrying before 00:00 UTC does not help. On the Billing page of the portal an organization admin can add Extra 256k requests and 4 GB a day blocks ($32 / month each, up to 7, an overage that raises both daily quotas) or upgrade to Unlimited, which drops the quota. Either takes effect within a few minutes.
Unlimited and Enterprise
Section titled “Unlimited and Enterprise”No daily quota. On Unlimited the rate limits below still apply; Enterprise has no API rate limits.
Rate limits
Section titled “Rate limits”| Plan | Limits |
|---|---|
| Free | 30 req/s, 10 concurrent calls and 18 transaction POSTs per second per client IP; bot traffic (no browser Referer or Origin) 5 req/s per IP; 1000 req/s per site |
| Boost | 120 req/s per client IP, split across the region's edges |
| Unlimited | 600 req/s per client IP, split across the region's edges |
| Enterprise | No API rate limit (Unlimited’s features otherwise); the IPFS gateway limit below still applies |
| IPFS gateway | 100 req/s per IP for Algorand mainnet assets, 10 req/s for other content |
Over a rate limit, the edge answers at once with a plain 429, without the JSON body. Wait and retry with exponential backoff.
Added latency
Section titled “Added latency”On Free and Boost the edges add 50 ms or more to backend and bot requests: those without a browser Referer. Browser apps and msgpack requests (?format=msgp) get none. Unlimited and Enterprise get none at all.
Telling the two 429s apart
Section titled “Telling the two 429s apart”A 429 with a JSON body whose message is “Daily Boost quota exceeded” means the daily quota is used up: stop until 00:00 UTC. Any other 429 is a rate limit: back off and retry. In browsers, read the body rather than the headers: cross-origin scripts may not be allowed to read Retry-After or X-And-Quota.
async function callNodely(url, init = {}, attempt = 0) { const res = await fetch(url, init); if (res.status !== 429) return res;
if (res.headers.get("content-type")?.includes("application/json")) { const body = await res.clone().json().catch(() => null); if (body?.message === "Daily Boost quota exceeded") return res; // wait for 00:00 UTC } if (attempt >= 5) return res;
// Rate limit: exponential backoff with jitter. await new Promise((resolve) => setTimeout(resolve, 250 * 2 ** attempt + Math.random() * 250)); return callNodely(url, init, attempt + 1);}Staying within limits
Section titled “Staying within limits”- Cache what does not change. Blocks and confirmed transactions are immutable: fetch them once.
- Ask for new data only, for example with
min-roundon indexer searches, instead of polling from round 0 or 1. - Reuse connections with HTTP/2 or keep-alive: see API speedup.
- Limit concurrency: on the free tier, no more than 10 calls at once, 2 for blocks and 1 for a paginating request (
next=). - Do not send the same request from many servers in the same round.
The full free-tier rules are in the fair usage policy.