Retry any function with exponential backoff. Zero dependencies, fully typed.
npm install retry-on-failimport { withRetry } from "retry-on-fail";
const data = await withRetry(() =>
fetch("https://api.example.com/users").then((r) => r.json())
);Retries up to 3 times with a 500 ms → 1 s → 2 s backoff by default.
withRetry(fn, options?)| Parameter | Type | Default | Description |
|---|---|---|---|
fn |
() => T | Promise<T> |
— | Function to call. Sync or async. |
options.retries |
number |
3 |
Max retry attempts after the first failure. |
options.delay |
number |
500 |
Initial delay in ms. Doubles with each attempt. |
Returns Promise<T>. Resolves with the first successful result, or rejects after all retries are exhausted.
const result = await withRetry(fetchReport, { retries: 5, delay: 1000 });
// Waits: 1 s → 2 s → 4 s → 8 s → 16 sAborting the signal stops retries immediately — the error propagates to the caller.
const controller = new AbortController();
const data = await withRetry(() =>
fetch("/api/report", { signal: controller.signal }).then((r) => r.json())
);
controller.abort(); // no retries; error propagates to the callerIf every attempt throws, withRetry rejects with the error from the last attempt.
try {
await withRetry(unstableOperation, { retries: 2 });
} catch (err) {
console.error("All retries exhausted:", err);
}MIT