Retry policy for 429 and 5xx responses — the only statuses Synctera's docs confirm are never served from their idempotency cache, and so are always safe to retry without risking a duplicate side effect.
Summary
Functions
Computes the delay in milliseconds before the next retry attempt (0-indexed),
using exponential backoff with jitter, unless an explicit retry_after_ms
(from a Retry-After header) is given, in which case that takes priority.
Parses a Retry-After header value, which may be either a number of
seconds or an HTTP-date, into milliseconds. Returns nil if the header is
absent or unparsable.
True for status codes Synctera's idempotency layer never caches, so they're always safe to retry.
Types
@type t() :: %Synctera.Retry{ base_delay_ms: non_neg_integer(), max_delay_ms: non_neg_integer(), max_retries: non_neg_integer() }
Functions
@spec backoff_delay_ms(non_neg_integer(), t(), non_neg_integer() | nil) :: non_neg_integer()
Computes the delay in milliseconds before the next retry attempt (0-indexed),
using exponential backoff with jitter, unless an explicit retry_after_ms
(from a Retry-After header) is given, in which case that takes priority.
@spec parse_retry_after(String.t() | nil) :: non_neg_integer() | nil
Parses a Retry-After header value, which may be either a number of
seconds or an HTTP-date, into milliseconds. Returns nil if the header is
absent or unparsable.
@spec retryable_status?(pos_integer()) :: boolean()
True for status codes Synctera's idempotency layer never caches, so they're always safe to retry.