HTTP APIs

larsggu.meReference › rate limit headers

rate limit headers

RateLimit-Limit / RateLimit-Remaining / RateLimit-Reset / Retry-After

The response headers by which a service tells a caller how much of its quota is left and when it resets, so the caller can pace itself rather than discover the limit by being refused.

Description

A limit that is only visible when it is exceeded produces callers that hammer until they are refused, then hammer again. Publishing the counter on every response turns that into a cooperative arrangement: the caller can see the remaining allowance drop, slow down before it reaches zero, and schedule around the reset.

Three values carry the state. The ceiling for the current window, the number of requests still available in it, and the moment the window rolls over. The third is the one callers most often ignore, and it is the one that makes pacing possible rather than reactive.

When the allowance is spent, the refusal carries status 429 and a Retry-After value. That value is an instruction, not a suggestion, and a caller that retries earlier ordinarily finds the penalty extended. Retrying at exactly the stated instant is almost as bad across a fleet, because every client does it at once; adding a small random offset spreads the return.

Limits are ordinarily scoped per credential rather than per address, which matters for anything running behind shared egress. Where a service publishes several limits at once, the headers name each one, and the caller has to respect the tightest rather than the first it parses.

Fields

Fields of rate limit headers
FieldFormMeaning
RateLimit-LimitintegerRequests permitted in the current window.
RateLimit-RemainingintegerRequests still available in it.
RateLimit-Resetseconds or instantWhen the window rolls over and the allowance returns.
Retry-Afterseconds or HTTP-dateAccompanies 429 and 503. The earliest acceptable retry.
Scopecredential or tenantWhat the counter is measured against.

Example

Approaching and crossing the limit

HTTP/1.1 200 OK
RateLimit-Limit: 600
RateLimit-Remaining: 4
RateLimit-Reset: 27

# the allowance is spent

HTTP/1.1 429 Too Many Requests
RateLimit-Limit: 600
RateLimit-Remaining: 0
Retry-After: 27
{"error":{"type":"rate_limited","message":"Request allowance exhausted."}}

The caller can see four requests left and a window rolling over in twenty-seven seconds before it is ever refused.

Failure modes

  • Reading only the status and ignoring the counter, so the caller learns the limit by hitting it every window.
  • Retrying at exactly the reset instant across a whole fleet, which recreates the spike.
  • Counting retries against the same allowance without accounting for them, which turns one refusal into a sustained one.
  • Assuming the limit is per address when it is per credential, and adding egress addresses in the hope of more allowance.

Topic: Transport. Last modified 2026-09-06.