type AsyncClosable = { close(): void | Promise } | (() => void | Promise) | AsyncDisposable | Disposable; /** * @see AsyncDisposableStack */ export class AsyncCloser implements AsyncDisposable { closers: Array = []; defer(closer: AsyncClosable | null | undefined) { if (!closer) { return; } this.closers.push(closer); } add(closer: T): T { if (!closer) { return closer; } this.closers.push(closer); return closer; } async [Symbol.asyncDispose]() { for (let closer of this.closers) { let o: unknown; if (typeof closer === 'function') { o = closer(); } else if (Symbol.asyncDispose in closer) { o = closer[Symbol.asyncDispose](); } else if (Symbol.dispose in closer) { closer[Symbol.dispose](); } else { o = closer.close(); } if (o && typeof (o as PromiseLike).then === 'function') { await o; } } } close() { return this[Symbol.asyncDispose](); } }