blob: f6ce775f82bb5ef3f107ec7961abec14f1adae7d (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
|
const ensurePromise = <T>(maybePromise: T | PromiseLike<T>): Promise<T> =>
typeof maybePromise === 'object' &&
maybePromise !== null &&
'then' in maybePromise &&
typeof maybePromise.then === 'function' &&
'catch' in maybePromise &&
typeof maybePromise.catch === 'function' &&
'finally' in maybePromise &&
typeof maybePromise.finally === 'function'
? (maybePromise as Promise<T>)
: Promise.resolve(maybePromise);
/** Returns a function that caches successful promises until time runs out, and throws away unsuccessful ones */
export const oncePromise = <T>(create: () => Promise<T>, timeout = -1) => {
let getPromise = (): Promise<T> => {
const oldGetPromise = getPromise,
promise = ensurePromise(create()).catch((e) => {
getPromise = oldGetPromise;
throw e;
}),
expires = timeout > 0 ? performance.now() + timeout : 0;
return (getPromise = expires
? ((() =>
performance.now() > expires
? oldGetPromise()
: promise) as () => Promise<T>)
: () => promise)();
};
return () => getPromise();
};
export default oncePromise;
|