Write withTimeout(promise, ms). It returns a new promise. If promise settles within ms milliseconds, the new promise settles the same way: it fulfills with the same value or rejects with the same reason.
If ms pass first, it rejects with an Error whose name is "TimeoutError" (the message is up to you). Once promise has settled, clear the timer, so nothing is left scheduled.
try {
const user = await withTimeout(fetchJson("/api/user"), 2000);
showUser(user);
} catch (error) {
if (error.name === "TimeoutError") showMessage("The server is taking too long.");
else throw error;
}
const clock = useFakeTimers();
const data = new Promise((resolve) => setTimeout(resolve, 100, "data"));
let result;
withTimeout(data, 200).then((value) => {
result = value;
});
await clock.tickAsync(100);
expect(result).toBe("data");
const clock = useFakeTimers();
const error = new Error("server error");
const failing = new Promise((_, reject) => setTimeout(reject, 50, error));
failing.catch(() => {}); // mark it handled, so it's never reported as unhandled
let reason;
withTimeout(failing, 100).catch((e) => {
reason = e;
});
await clock.tickAsync(50);
expect(reason).toBe(error);
const clock = useFakeTimers();
let reason;
withTimeout(new Promise(() => {}), 100).catch((e) => {
reason = e;
});
await clock.tickAsync(99);
expect(reason).toBeUndefined();
await clock.tickAsync(1);
expect(reason).toBeDefined();
const clock = useFakeTimers();
let reason;
withTimeout(new Promise(() => {}), 100).catch((e) => {
reason = e;
});
await clock.tickAsync(100);
expect(reason).toBeInstanceOf(Error);
expect(reason.name).toBe("TimeoutError");
const clock = useFakeTimers();
withTimeout(Promise.resolve("fast"), 1000);
await flush();
expect(clock.pending()).toBe(0);
const clock = useFakeTimers();
const failing = Promise.reject(new Error("fast failure"));
failing.catch(() => {}); // mark it handled, so it's never reported as unhandled
withTimeout(failing, 1000).catch(() => {}); // it rejects too; this test only checks the timer
await flush();
expect(clock.pending()).toBe(0);
Run tests runs every test on your code, here in your browser. The problem is solved when they all pass.
Ctrl + Enter runs the tests (⌘ + Enter on a Mac).
I'm here to help with Promise with a timeout. I give hints, never the solution, so you get to solve it yourself. Ask for a hint, select code to ask about it, or press Ask Tuto why on a failing test.
Your first 3 answers need no account. for free to keep asking.