Rate limits are enforced per tenant, tiered by plan, using an atomic Lua token-bucket script against Redis — no INCR/EXPIRE race condition that could let a burst slip through.

Default limits

Auth endpoints carry a separate, stricter per-IP limit independent of plan tier — this is what actually protects against credential-stuffing, since an attacker doesn’t have a valid tenant token yet.

Response headers

A rate-limited response returns 429. Attacker-facing rate-limit headers (remaining quota, reset time) are deliberately suppressed on the auth endpoints specifically — informational for normal API use, but a 429 with “here’s exactly how many attempts you have left” is a gift to a credential-stuffing script. Standard API endpoints do return the usual X-RateLimit-* headers.

What counts against your limit

Every authenticated request to /api/v1/*. Health checks (/health, /health/ready) are excluded.

Errors