Rate Limits & Quotas
Each API key is subject to per-minute request limits and concurrency caps to
ensure fair use and stable service for all customers. This page documents the
fixed input caps and how to handle 429 rate_limited responses.
Per-request input caps
These hard caps are enforced on every request. Exceeding the text cap returns
400 validation_error; oversized or over-length audio returns
413 validation_error (or 400 validation_error when the over-length
duration is detected by probing).
| Endpoint | Maximum input per request |
|---|---|
POST /v1/tts | 500 characters of text |
POST /v1/stt | 50 MB file / 30 minutes of audio |
Request-rate & concurrency limits
Per-minute request limits and concurrency caps are enforced per API key, not
per account or IP. Unlike the input caps above, these values are
policy-driven — they are set server-side per key and can change without a
redeploy — so no fixed public number is published here. When you exceed your
request-rate limit the API returns 429 rate_limited; when too many requests
are in flight at once it returns 429 concurrency_limit_exceeded. Calls to a
free model are additionally capped by its 60-minute monthly allowance
(429 quota_exceeded) — see Free allowances. Need
higher limits for your key? Contact
api@revolab.ai.
Discovery endpoints (GET /v1/voices, GET /v1/models) have
their own generous, non-billable request bucket — normal SDK usage (listing
once per session) never sees it; only a runaway request loop is throttled.
Note that requests rejected with validation errors (4xx) still count toward your request-rate window — the limiter runs before validation, by design, so malformed traffic cannot bypass it. Only the rate window is consumed; nothing is billed.
Rate limit response
When a limit is exceeded, the API returns HTTP 429 with the standard /v1/
error envelope:
{
"error": {
"code": "rate_limited",
"message": "Rate limit exceeded.",
"request_id": "req_01HXYZ...",
"retry_after": 12
}
}The Retry-After HTTP header is also set with the same value in seconds.
To back off before hitting a 429, read the rate-limit headers returned on every billable response:
X-RateLimit-Limit— the maximum requests allowed in the current window.X-RateLimit-Remaining— requests remaining in the current window.X-RateLimit-Reset— seconds until the window resets.
Retry & exponential back-off
We recommend exponential back-off with jitter when handling 429 responses:
- On first 429: wait
retry_afterseconds from the response body. - On subsequent 429s: double the wait time each retry (cap at 64 s).
- Jitter: add a random 0–500 ms to each wait to avoid thundering herd.
- After 5 retries with no success, surface the error to the user.
Higher limits
If your use case requires higher RPM, concurrent requests, or text length limits, contact api@revolab.ai.