GET requests, and requests that carry an Idempotency-Key header. Every other
request is sent once.
What is retried
500 and other errors are not retried. The Idempotency-Key header can come
from the call’s input or from headers configured on the client. The clients
retry any request that carries one, so send it only to endpoints that declare
an Idempotency-Key header; many endpoints that change data do not.
Between attempts, a client waits for the delay in the response’s Retry-After
header, given in seconds or as an HTTP date. Without one, it waits a random
time between zero and min(2 s, 250 ms × 2^(attempt - 1)): up to 250 ms before
the second attempt and up to 500 ms before the third.
If Retry-After asks for more than the client’s limit, 60 seconds by default,
the client does not wait and does not shorten the delay: it stops retrying and
handles that response as the result, which is an error for an error status. When
attempts run out, the last response is handled the same way. When a network
error or timeout ends the call, TypeScript throws TransportError, Python
raises TransportError, and Rust returns Error::Transport or
Error::Timeout.
Timeouts
No client limits the whole call: the timeout applies within each attempt, so a call that is retried can take longer than one timeout.- TypeScript:
timeoutMsaborts an attempt that has not finished in time. To cancel a whole call, pass anAbortSignalassignalin the call’s second argument. Cancelling stops the current attempt and any wait, and the call throwsTransportErrorwith the signal’s abort reason as itscause. - Python:
timeoutis passed tohttpxfor each attempt, which applies it separately to connecting, writing, reading, and waiting for a pooled connection. - Rust:
timeoutlimits each attempt from sending to the end of the response body. The default HTTP client also uses it as its connect timeout.
Configure retries and timeouts
Attempts are limited to between 1 and 3; a larger value means 3.
Idempotency keys
Endpoints that create or change something often take anIdempotency-Key
header, which identifies one logical change across retries. Most of them
require it, and the API answers 400 with IDEMPOTENCY_KEY_REQUIRED when it is
missing. The key is 1 to 255 visible ASCII characters, without spaces. When the API answers
with a stored result for a key it has already seen, the response has
Idempotent-Replayed: true.
The clients do not create keys. Pass one in the call’s input:
- TypeScript:
headers: { idempotencyKey }, orheaders: { "idempotency-key": key }where the contract spells the header that way, as foruploadAttachment. - Python:
"headers": { "Idempotency-Key": key }in the input model, with the header name spelled as the contract spells it. - Rust: a positional argument when the endpoint requires the key, or the
idempotency_keysetter of the operation’sParamswhen it is optional.
Idempotency-Key in the client’s headers option: every call would
share one key.