2024-01-01 21:11:32 +00:00
|
|
|
// Copyright 2018-2024 the Deno authors. All rights reserved. MIT license.
|
2022-03-01 04:25:50 +00:00
|
|
|
// This module is browser compatible.
|
2021-08-17 05:04:21 +00:00
|
|
|
|
2023-12-01 02:19:22 +00:00
|
|
|
/** Options for {@linkcode delay}. */
|
2021-08-17 05:04:21 +00:00
|
|
|
export interface DelayOptions {
|
2022-11-25 11:40:23 +00:00
|
|
|
/** Signal used to abort the delay. */
|
2021-08-17 05:04:21 +00:00
|
|
|
signal?: AbortSignal;
|
2022-11-25 11:40:23 +00:00
|
|
|
/** Indicates whether the process should continue to run as long as the timer exists.
|
|
|
|
*
|
|
|
|
* @default {true}
|
|
|
|
*/
|
2022-08-22 13:09:53 +00:00
|
|
|
persistent?: boolean;
|
2021-08-17 05:04:21 +00:00
|
|
|
}
|
|
|
|
|
2022-11-25 11:40:23 +00:00
|
|
|
/**
|
2023-12-01 02:19:22 +00:00
|
|
|
* Resolve a {@linkcode Promise} after a given amount of milliseconds.
|
2022-11-25 11:40:23 +00:00
|
|
|
*
|
2024-06-21 06:37:23 +00:00
|
|
|
* @throws {DOMException} If the optional signal is aborted before the delay
|
|
|
|
* duration, and `signal.reason` is undefined.
|
2024-05-22 00:40:43 +00:00
|
|
|
* @param ms Duration in milliseconds for how long the delay should last.
|
|
|
|
* @param options Additional options.
|
|
|
|
*
|
2024-05-22 05:08:36 +00:00
|
|
|
* @example Basic usage
|
2024-06-03 04:10:27 +00:00
|
|
|
* ```ts no-assert
|
2024-04-29 02:57:30 +00:00
|
|
|
* import { delay } from "@std/async/delay";
|
2022-11-25 11:40:23 +00:00
|
|
|
*
|
|
|
|
* // ...
|
|
|
|
* const delayedPromise = delay(100);
|
|
|
|
* const result = await delayedPromise;
|
|
|
|
* // ...
|
|
|
|
* ```
|
|
|
|
*
|
2024-05-22 05:08:36 +00:00
|
|
|
* @example Disable persistence
|
|
|
|
*
|
|
|
|
* Setting `persistent` to `false` will allow the process to continue to run as
|
|
|
|
* long as the timer exists.
|
2022-11-25 11:40:23 +00:00
|
|
|
*
|
2024-09-19 23:29:31 +00:00
|
|
|
* ```ts no-assert ignore
|
2024-04-29 02:57:30 +00:00
|
|
|
* import { delay } from "@std/async/delay";
|
2022-11-25 11:40:23 +00:00
|
|
|
*
|
|
|
|
* // ...
|
|
|
|
* await delay(100, { persistent: false });
|
|
|
|
* // ...
|
|
|
|
* ```
|
|
|
|
*/
|
2021-08-17 05:04:21 +00:00
|
|
|
export function delay(ms: number, options: DelayOptions = {}): Promise<void> {
|
2024-04-11 21:23:54 +00:00
|
|
|
const { signal, persistent = true } = options;
|
2023-07-14 05:03:05 +00:00
|
|
|
if (signal?.aborted) return Promise.reject(signal.reason);
|
2022-08-24 01:21:57 +00:00
|
|
|
return new Promise((resolve, reject) => {
|
2021-08-17 05:04:21 +00:00
|
|
|
const abort = () => {
|
|
|
|
clearTimeout(i);
|
2023-07-14 05:03:05 +00:00
|
|
|
reject(signal?.reason);
|
2021-08-17 05:04:21 +00:00
|
|
|
};
|
|
|
|
const done = () => {
|
|
|
|
signal?.removeEventListener("abort", abort);
|
|
|
|
resolve();
|
|
|
|
};
|
|
|
|
const i = setTimeout(done, ms);
|
|
|
|
signal?.addEventListener("abort", abort, { once: true });
|
2022-08-22 13:09:53 +00:00
|
|
|
if (persistent === false) {
|
2022-09-07 11:19:59 +00:00
|
|
|
try {
|
|
|
|
// @ts-ignore For browser compatibility
|
|
|
|
Deno.unrefTimer(i);
|
|
|
|
} catch (error) {
|
|
|
|
if (!(error instanceof ReferenceError)) {
|
|
|
|
throw error;
|
|
|
|
}
|
2024-09-13 05:43:13 +00:00
|
|
|
// deno-lint-ignore no-console
|
2022-09-07 11:19:59 +00:00
|
|
|
console.error("`persistent` option is only available in Deno");
|
|
|
|
}
|
2022-08-22 13:09:53 +00:00
|
|
|
}
|
2021-08-17 05:04:21 +00:00
|
|
|
});
|
2020-05-09 12:34:47 +00:00
|
|
|
}
|