Files
HealthLog/src/lib/async/settle-within.ts
T
Marc-André Bombeck b4e3e22d43 fix(ssr): clear the budget timer once a raced read answers
The mood and dashboard prefetches and the sign-in location lookup raced
their work against a bare setTimeout that was never cleared, leaving
one live timer behind per render or sign-in after the work had already
answered. A shared helper races the work and clears the timer.
2026-10-08 22:57:47 +02:00

25 lines
812 B
TypeScript

/**
* Wait for `work` at most `ms`, then settle with `fallback` instead.
*
* The budget timer is cleared as soon as either side settles. A bare
* `Promise.race` against a `setTimeout` left the timer running after the
* work had long answered: one live timer per server render or per audited
* sign-in, each holding its closure until it fired. `work` is not
* cancelled; a rejection of `work` inside the budget rejects here too.
*/
export async function settleWithin<T, F>(
work: Promise<T>,
ms: number,
fallback: F,
): Promise<T | F> {
let timer: ReturnType<typeof setTimeout> | undefined;
const budget = new Promise<F>((resolve) => {
timer = setTimeout(() => resolve(fallback), ms);
});
try {
return await Promise.race([work, budget]);
} finally {
clearTimeout(timer);
}
}