通常の await
// ただ1秒待つだけの関数
async function sleepOneSec() {
await new Promise((resolve) => setTimeout(resolve, 1000));
}
async function main() {
await sleepOneSec();
}
// 実行
main();
await
with timeout
/**
* await にタイムアウトを設定する
*
* timeoutを超えて await で待機すると UnhandledPromiseRejection 例外が throw されます。
* @param {Promise} promise - 実行したい promise 関数
* @param {number} timeout - タイムアウト(ms)
* @returns Promise<T>
*/
export function withTimeout<T>(promise: Promise<T>, timeout: number) {
const errorMessage = `await での待機が ${timeout}ms を超えました`;
const timeoutPromise: Promise<T> = new Promise((_, reject) =>
setTimeout(() => reject(errorMessage), timeout),
);
// Promise.race()を利用して先に解決した方を優先する
return Promise.race([
promise, // 本来実行したい promise 関数
timeoutPromise, // こちらの方が早く解決すると reject()
]);
}
// ただ1秒待つだけの関数
async function sleepOneSec() {
await new Promise((resolve) => setTimeout(resolve, 1000));
}
async function main() {
// OK (タイムアウト2秒)
await withTimeout(sleepOneSec(), 2000);
// NG (タイムアウト0.5秒)
await withTimeout(sleepOneSec(), 500);
/*
[ERROR] 19:45:13 UnhandledPromiseRejection:
This error originated either by throwing inside of an async function without a catch block,
or by rejecting a promise which was not handled with .catch().
The promise rejected with the reason "await での待機が 500ms を超えました".
*/
}
// 実行
main();
await
で長時間待ちたくない時によいな…と思ってたのですが await-timeout なるものが既にありました。