MiddleCodeVery commonNot answered yet
How do you write a retry helper retrying only transient errors with backoff plus jitter that honors ctx?
Implement a retry helper for an idempotent operation. It must retry only on transient errors, back off exponentially, randomize the delay, cap the attempts, and abort the moment the caller's ctx is done.
Constraints:
- retry only when
isTransient(err)is true; any other error returns immediately - exponential backoff
base * 2^n(1s, 2s, 4s, ...) plus random jitter so clients de-correlate - stop after
maxAttemptsand return the last error - between attempts,
selectonctx.Done()— a cancelled or expiredctxaborts and returnsctx.Err() - assume
isTransient(error) boolis provided
func retry(ctx context.Context, maxAttempts int, base time.Duration, op func() error) error {
// your code here
}
Write the implementation.
Loop up to a fixed attempt cap calling op; on success return nil, retry only on a transient error, else return it. Between attempts sleep base*2^n (1s, 2s, 4s) plus random jitter, and select on ctx.Done() so a cancelled ctx aborts mid-wait.
- ✗Retrying non-idempotent or non-transient errors, duplicating side effects or hammering a permanent failure
- ✗Backing off without jitter, so all clients retry in lockstep and create a synchronized thundering herd
- ✗Sleeping with a bare
time.Sleepthat ignoresctx, so a cancelled call keeps waiting out the full backoff
- →Why add jitter instead of a fixed offset between retries?
- →How does a retry budget prevent retry amplification across a chain?