evnty 5.3.3 → 5.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/build/async.cjs +16 -16
- package/build/async.cjs.map +1 -1
- package/build/async.d.ts +8 -0
- package/build/async.js +10 -16
- package/build/async.js.map +1 -1
- package/build/broadcast.cjs +4 -13
- package/build/broadcast.cjs.map +1 -1
- package/build/broadcast.js +5 -14
- package/build/broadcast.js.map +1 -1
- package/build/event.cjs +5 -16
- package/build/event.cjs.map +1 -1
- package/build/event.js +6 -17
- package/build/event.js.map +1 -1
- package/build/iterator.cjs +11 -40
- package/build/iterator.cjs.map +1 -1
- package/build/iterator.js +11 -40
- package/build/iterator.js.map +1 -1
- package/build/sequence.cjs +8 -9
- package/build/sequence.cjs.map +1 -1
- package/build/sequence.js +8 -9
- package/build/sequence.js.map +1 -1
- package/build/utils.cjs +32 -46
- package/build/utils.cjs.map +1 -1
- package/build/utils.js +32 -46
- package/build/utils.js.map +1 -1
- package/package.json +9 -8
- package/src/async.ts +17 -9
- package/src/broadcast.ts +5 -5
- package/src/event.ts +8 -10
- package/src/iterator.ts +11 -10
- package/src/sequence.ts +8 -9
- package/src/utils.ts +26 -25
package/build/utils.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/utils.ts"],"sourcesContent":["import { Sequence } from './sequence.js';\nimport { AnyIterator, AnyIterable, MaybePromise } from './types.js';\n\n/**\n * @internal\n */\nexport function isThenable(value: unknown): value is PromiseLike<unknown> {\n return value !== null && typeof value === 'object' && typeof (value as PromiseLike<unknown>).then === 'function';\n}\n\n/**\n * @internal\n * A no-operation function. Useful as a default callback or placeholder.\n */\nexport const noop = () => {};\n\n/**\n * @internal\n * Returns the minimum value from an iterable, or a fallback if empty.\n */\nexport function min(values: Iterable<number>, fallback: number): number {\n let result = Infinity;\n for (const value of values) {\n if (value < result) result = value;\n }\n return result === Infinity ? fallback : result;\n}\n\n/**\n * @internal\n * Indicates which iterator method triggered a mapping operation.\n */\nexport enum MapIteratorType {\n /** The next() method was called */\n NEXT,\n /** The return() method was called */\n RETURN,\n /** The throw() method was called */\n THROW,\n}\n\n/**\n * @internal\n * A mapping function for transforming iterator results.\n * @template T - The input value type\n * @template U - The output value type\n * @template TReturn - The iterator return type\n */\nexport interface MapNext<T, U, TReturn> {\n (result: MaybePromise<IteratorResult<T, TReturn>>, type: MapIteratorType): MaybePromise<IteratorResult<U, TReturn>>;\n}\n\n/**\n * @internal\n * Wraps an iterator with a mapping function applied to each result.\n * @template U - The output value type\n * @template T - The input value type\n * @template TReturn - The iterator return type\n * @template TNext - The type passed to next()\n * @param iterator - The source iterator to wrap\n * @param map - The mapping function to apply to each result\n * @returns An async iterator with mapped results\n */\nexport const mapIterator = <U, T, TReturn, TNext>(iterator: AnyIterator<T, TReturn, TNext>, map: MapNext<T, U, TReturn>): AsyncIterator<U, TReturn, TNext> => {\n const subIterator: AsyncIterator<U, TReturn, TNext> = {\n next: async (...args: [] | [TNext]) => {\n const result = await iterator.next(...args);\n return map(result, MapIteratorType.NEXT);\n },\n };\n if (iterator.return) {\n subIterator.return = async (...args: [] | [TReturn]) => {\n const result = await iterator.return!(...args);\n return map(result, MapIteratorType.RETURN);\n };\n } else {\n subIterator.return = async (value: TReturn) => {\n return map({ done: true, value }, MapIteratorType.RETURN);\n };\n }\n if (iterator.throw) {\n subIterator.throw = async (...args: [] | [unknown]) => {\n const result = await iterator.throw!(...args);\n return map(result, MapIteratorType.THROW);\n };\n }\n\n return subIterator;\n};\n\n/**\n * Wraps an async iterable with abort signal support.\n * Each iteration creates a fresh iterator with scoped abort handling.\n * Listener is added at iteration start and removed on completion/abort/return.\n *\n * @template T - The yielded value type\n * @template TReturn - The return value type\n * @template TNext - The type passed to next()\n * @param iterable - The source async iterable to wrap\n * @param signal - AbortSignal to cancel iteration\n * @returns An async iterable with abort support\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * const source = async function*() { yield 1; yield 2; yield 3; };\n *\n * for await (const value of abortableIterable(source(), controller.signal)) {\n * console.log(value);\n * if (value === 2) controller.abort();\n * }\n * ```\n */\nexport function abortableIterable<T, TReturn, TNext>(iterable: AsyncIterable<T, TReturn, TNext>, signal: AbortSignal): AsyncIterable<T, TReturn, TNext> {\n return {\n [Symbol.asyncIterator](): AsyncIterator<T, TReturn, TNext> {\n const iterator = iterable[Symbol.asyncIterator]();\n const { promise, resolve } = Promise.withResolvers<void>();\n const onAbort = () => resolve();\n let closed = false;\n\n const finish = (value?: TReturn): Promise<IteratorResult<T, TReturn>> => {\n if (closed) {\n return Promise.resolve({ done: true, value: value as TReturn });\n }\n closed = true;\n signal.removeEventListener('abort', onAbort);\n return iterator.return?.(value) ?? Promise.resolve({ done: true, value: value as TReturn });\n };\n\n if (signal.aborted) {\n onAbort();\n } else {\n signal.addEventListener('abort', onAbort);\n }\n\n const race = [promise, undefined] as unknown as [Promise<void>, Promise<IteratorResult<T, TReturn>>];\n\n return {\n async next(...args: [] | [TNext]): Promise<IteratorResult<T, TReturn>> {\n race[1] = iterator.next(...args);\n const result = await Promise.race(race);\n if (result === undefined) {\n void finish();\n return { done: true, value: undefined as TReturn };\n }\n if (result.done) {\n closed = true;\n signal.removeEventListener('abort', onAbort);\n }\n return result;\n },\n async return(value?: TReturn): Promise<IteratorResult<T, TReturn>> {\n return finish(value);\n },\n };\n },\n };\n}\n\n/**\n * Interface for creating iterable number sequences with various parameter combinations.\n * Supports infinite sequences, counted sequences, and sequences with custom start and step values.\n */\nexport interface Iterate {\n (): Iterable<number, void, unknown>;\n (count: number): Iterable<number, void, unknown>;\n (start: number, count: number): Iterable<number, void, unknown>;\n (start: number, count: number, step: number): Iterable<number, void, unknown>;\n}\n\n/**\n * Creates an iterable sequence of numbers with flexible parameters.\n * Can generate infinite sequences, finite sequences, or sequences with custom start and step values.\n *\n * @param args Variable arguments to configure the sequence:\n * - No args: Infinite sequence starting at 0 with step 1\n * - 1 arg (count): Sequence from 0 to count-1\n * - 2 args (start, count): Sequence starting at 'start' for 'count' iterations\n * - 3 args (start, count, step): Custom start, count, and step value\n * @returns An iterable that generates numbers according to the parameters\n *\n * @example\n * ```typescript\n * // Infinite sequence: 0, 1, 2, 3, ...\n * for (const n of iterate()) { }\n *\n * // Count only: 0, 1, 2, 3, 4\n * for (const n of iterate(5)) { }\n *\n * // Start and count: 10, 11, 12, 13, 14\n * for (const n of iterate(10, 5)) { }\n *\n * // Start, count, and step: 0, 2, 4, 6, 8\n * for (const n of iterate(0, 5, 2)) { }\n * ```\n */\nexport const iterate: Iterate = (startOrCount?: number, countWhenTwoArgs?: number, step: number = 1): Iterable<number, void, unknown> => {\n const hasStartArg = countWhenTwoArgs !== undefined;\n const start = hasStartArg ? startOrCount! : 0;\n const count = startOrCount === undefined ? Infinity : hasStartArg ? countWhenTwoArgs : startOrCount;\n\n return {\n [Symbol.iterator]() {\n let idx = 0;\n let current = start;\n return {\n next() {\n if (idx < count) {\n const value = current;\n current += step;\n idx++;\n return { value, done: false };\n }\n return { value: undefined, done: true };\n },\n return(value) {\n idx = count;\n return { value, done: true };\n },\n throw(error?: unknown) {\n idx = count;\n throw error;\n },\n } satisfies Iterator<number, void, unknown>;\n },\n };\n};\n\n/**\n * @internal\n * Creates a promise that resolves after a specified timeout. If an `AbortSignal` is provided and triggered,\n * the timeout is cleared, and the promise resolves to `false`.\n *\n * @param {number} timeout - The time in milliseconds to wait before resolving the promise.\n * @param {AbortSignal} [signal] - An optional `AbortSignal` that can abort the timeout.\n * @returns {Promise<boolean>} A promise that resolves to `true` if the timeout completed, or `false` if it was aborted.\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * setTimeout(() => controller.abort(), 500);\n * const result = await setTimeoutAsync(1000, controller.signal);\n * console.log(result); // false\n * ```\n */\nexport const setTimeoutAsync = async (timeout: number, signal?: AbortSignal): Promise<boolean> => {\n if (signal?.aborted) {\n return false;\n }\n const { promise, resolve } = Promise.withResolvers<boolean>();\n const timerId = setTimeout(resolve, timeout, true);\n const onAbort = () => {\n clearTimeout(timerId);\n resolve(false);\n };\n signal?.addEventListener('abort', onAbort);\n\n return promise.finally(() => signal?.removeEventListener('abort', onAbort));\n};\n\n/**\n * Converts a synchronous iterable to an asynchronous iterable.\n * Wraps the sync iterator methods to return promises, enabling uniform async handling.\n *\n * @template T The type of values yielded by the iterator\n * @template TReturn The return type of the iterator\n * @template TNext The type of value that can be passed to next()\n * @param iterable A synchronous iterable to convert\n * @returns An async iterable that yields the same values as the input\n *\n * @example\n * ```typescript\n * const syncArray = [1, 2, 3, 4, 5];\n * const asyncIterable = toAsyncIterable(syncArray);\n *\n * for await (const value of asyncIterable) {\n * console.log(value); // 1, 2, 3, 4, 5\n * }\n * ```\n */\nexport const toAsyncIterable = <T, TReturn, TNext>(iterable: Iterable<T, TReturn, TNext>): AsyncIterable<T, TReturn, TNext> => {\n return {\n [Symbol.asyncIterator]() {\n const iterator = iterable[Symbol.iterator]();\n return {\n async next(...args: [TNext] | []) {\n return iterator.next(...args);\n },\n async return(maybeValue) {\n const value = await maybeValue;\n return iterator.return?.(value) ?? ({ value, done: true } as IteratorResult<T, TReturn>);\n },\n async throw(error) {\n if (iterator.throw) {\n return iterator.throw(error);\n }\n throw error;\n },\n } satisfies AsyncIterator<T, TReturn, TNext>;\n },\n };\n};\n\n/**\n * @internal\n * Pipes values from an async iterable through a generator transformation.\n * Applies a generator function to each value, yielding all resulting values.\n * Supports cancellation via AbortSignal for early termination.\n *\n * @template T The input value type\n * @template U The output value type\n * @param iterable The source async iterable\n * @param generatorFactory A factory that returns a generator function for transforming values\n * @param signal Optional AbortSignal to cancel the operation\n * @returns An async generator yielding transformed values\n *\n * @example\n * ```typescript\n * async function* source() {\n * yield 1; yield 2; yield 3;\n * }\n *\n * const doubled = pipe(source(), () => async function*(n) {\n * yield n * 2;\n * });\n *\n * for await (const value of doubled) {\n * console.log(value); // 2, 4, 6\n * }\n * ```\n */\nconst isAsyncIterable = <T, TReturn, TNext>(value: AnyIterable<T, TReturn, TNext>): value is AsyncIterable<T, TReturn, TNext> => {\n return typeof (value as AsyncIterable<T, TReturn, TNext>)[Symbol.asyncIterator] === 'function';\n};\n\n/**\n * @internal\n */\nexport async function* pipe<T, U>(\n iterable: AsyncIterable<T>,\n generatorFactory: () => (value: T) => AnyIterable<U, void, unknown>,\n signal?: AbortSignal,\n): AsyncGenerator<Awaited<U>, void, unknown> {\n const source = signal ? abortableIterable(iterable, signal) : iterable;\n const generator = generatorFactory();\n\n for await (const value of source) {\n const produced = generator(value);\n const subIterable = isAsyncIterable(produced) ? produced : toAsyncIterable(produced);\n const abortableSub = signal ? abortableIterable(subIterable, signal) : subIterable;\n\n for await (const subValue of abortableSub) {\n yield subValue;\n }\n }\n}\n\n/**\n * @internal\n * Merges multiple async iterables into a single stream.\n * Values are yielded as they become available from any source.\n * Completes when all sources complete; aborts all on error.\n * @template T - The value type yielded by all iterables\n * @param iterables - The async iterables to merge\n * @returns A merged async iterable\n */\nexport const mergeIterables = <T>(...iterables: AsyncIterable<T, void, unknown>[]): AsyncIterable<T, void, unknown> => {\n return {\n [Symbol.asyncIterator]() {\n if (iterables.length === 0) {\n return {\n next: async () => ({ value: undefined, done: true }),\n };\n }\n\n const exit = Symbol('mergeIterables.exit');\n const ctrl = new AbortController();\n const sequence = new Sequence<T>(ctrl.signal);\n let remaining = iterables.length;\n\n const pump = async (iterable: AsyncIterable<T, void, unknown>) => {\n try {\n for await (const value of abortableIterable(iterable, ctrl.signal)) {\n if (!sequence.emit(value)) {\n break;\n }\n }\n } catch (error) {\n ctrl.abort(error);\n } finally {\n remaining -= 1;\n if (remaining === 0 && !ctrl.signal.aborted) {\n ctrl.abort(exit);\n }\n }\n };\n\n for (const iterable of iterables) {\n void pump(iterable);\n }\n\n return {\n next: async () => {\n try {\n const value = await sequence.receive();\n return { value, done: false };\n } catch {\n if (ctrl.signal.aborted && ctrl.signal.reason === exit) {\n return { value: undefined, done: true };\n }\n throw ctrl.signal.reason;\n }\n },\n return: async () => {\n ctrl.abort(exit);\n return { value: undefined, done: true };\n },\n throw: async (error?: unknown) => {\n ctrl.abort(error);\n return { value: undefined, done: true };\n },\n };\n },\n };\n};\n"],"names":["MapIteratorType","abortableIterable","isThenable","iterate","mapIterator","mergeIterables","min","noop","pipe","setTimeoutAsync","toAsyncIterable","value","then","values","fallback","result","Infinity","iterator","map","subIterator","next","args","return","done","throw","iterable","signal","Symbol","asyncIterator","promise","resolve","Promise","withResolvers","onAbort","closed","finish","removeEventListener","aborted","addEventListener","race","undefined","startOrCount","countWhenTwoArgs","step","hasStartArg","start","count","idx","current","error","timeout","timerId","setTimeout","clearTimeout","finally","maybeValue","isAsyncIterable","generatorFactory","source","generator","produced","subIterable","abortableSub","subValue","iterables","length","exit","ctrl","AbortController","sequence","Sequence","remaining","pump","emit","abort","receive","reason"],"mappings":"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"}
|
|
1
|
+
{"version":3,"sources":["../src/utils.ts"],"sourcesContent":["import { Sequence } from './sequence.js';\nimport { ITERATOR_DONE } from './async.js';\nimport { AnyIterator, AnyIterable, MaybePromise } from './types.js';\n\n/**\n * @internal\n */\nexport function isThenable(value: unknown): value is PromiseLike<unknown> {\n return value !== null && typeof value === 'object' && typeof (value as PromiseLike<unknown>).then === 'function';\n}\n\n/**\n * @internal\n * A no-operation function. Useful as a default callback or placeholder.\n */\nexport const noop = () => {};\n\n/**\n * @internal\n * Returns the minimum value from an iterable, or a fallback if empty.\n */\nexport function min(values: Iterable<number>, fallback: number): number {\n let result = Infinity;\n for (const value of values) {\n if (value < result) result = value;\n }\n return result === Infinity ? fallback : result;\n}\n\n/**\n * @internal\n * Indicates which iterator method triggered a mapping operation.\n */\nexport enum MapIteratorType {\n /** The next() method was called */\n NEXT,\n /** The return() method was called */\n RETURN,\n /** The throw() method was called */\n THROW,\n}\n\n/**\n * @internal\n * A mapping function for transforming iterator results.\n * @template T - The input value type\n * @template U - The output value type\n * @template TReturn - The iterator return type\n */\nexport interface MapNext<T, U, TReturn> {\n (result: MaybePromise<IteratorResult<T, TReturn>>, type: MapIteratorType): MaybePromise<IteratorResult<U, TReturn>>;\n}\n\n/**\n * @internal\n * Wraps an iterator with a mapping function applied to each result.\n * @template U - The output value type\n * @template T - The input value type\n * @template TReturn - The iterator return type\n * @template TNext - The type passed to next()\n * @param iterator - The source iterator to wrap\n * @param map - The mapping function to apply to each result\n * @returns An async iterator with mapped results\n */\nexport const mapIterator = <U, T, TReturn, TNext>(iterator: AnyIterator<T, TReturn, TNext>, map: MapNext<T, U, TReturn>): AsyncIterator<U, TReturn, TNext> => {\n const subIterator: AsyncIterator<U, TReturn, TNext> = {\n next: async (...args: [] | [TNext]) => {\n const result = await iterator.next(...args);\n return map(result, MapIteratorType.NEXT);\n },\n };\n if (iterator.return) {\n subIterator.return = async (...args: [] | [TReturn]) => {\n const result = await iterator.return!(...args);\n return map(result, MapIteratorType.RETURN);\n };\n } else {\n subIterator.return = async (value: TReturn) => {\n return map({ done: true, value }, MapIteratorType.RETURN);\n };\n }\n if (iterator.throw) {\n subIterator.throw = async (...args: [] | [unknown]) => {\n const result = await iterator.throw!(...args);\n return map(result, MapIteratorType.THROW);\n };\n }\n\n return subIterator;\n};\n\n/**\n * Wraps an async iterable with abort signal support.\n * Each iteration creates a fresh iterator with scoped abort handling.\n * Listener is added at iteration start and removed on completion/abort/return.\n *\n * @template T - The yielded value type\n * @template TReturn - The return value type\n * @template TNext - The type passed to next()\n * @param iterable - The source async iterable to wrap\n * @param signal - AbortSignal to cancel iteration\n * @returns An async iterable with abort support\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * const source = async function*() { yield 1; yield 2; yield 3; };\n *\n * for await (const value of abortableIterable(source(), controller.signal)) {\n * console.log(value);\n * if (value === 2) controller.abort();\n * }\n * ```\n */\nexport function abortableIterable<T, TReturn, TNext>(iterable: AsyncIterable<T, TReturn, TNext>, signal: AbortSignal): AsyncIterable<T, TReturn, TNext> {\n return {\n [Symbol.asyncIterator](): AsyncIterator<T, TReturn, TNext> {\n const iterator = iterable[Symbol.asyncIterator]();\n const { promise, resolve } = Promise.withResolvers<void>();\n const onAbort = () => resolve();\n let closed = false;\n\n const finish = (value?: TReturn): Promise<IteratorResult<T, TReturn>> => {\n if (closed) {\n return Promise.resolve({ done: true, value: value as TReturn });\n }\n closed = true;\n signal.removeEventListener('abort', onAbort);\n return iterator.return?.(value) ?? Promise.resolve({ done: true, value: value as TReturn });\n };\n\n if (signal.aborted) {\n onAbort();\n } else {\n signal.addEventListener('abort', onAbort);\n }\n\n const race = [promise, undefined] as unknown as [Promise<void>, Promise<IteratorResult<T, TReturn>>];\n\n return {\n next(...args: [] | [TNext]): Promise<IteratorResult<T, TReturn>> {\n race[1] = iterator.next(...args);\n return Promise.race(race).then((result) => {\n if (result === undefined) {\n void finish();\n return { done: true, value: undefined as TReturn } as IteratorResult<T, TReturn>;\n }\n if (result.done) {\n closed = true;\n signal.removeEventListener('abort', onAbort);\n }\n return result;\n });\n },\n return(value?: TReturn): Promise<IteratorResult<T, TReturn>> {\n return finish(value);\n },\n };\n },\n };\n}\n\n/**\n * Interface for creating iterable number sequences with various parameter combinations.\n * Supports infinite sequences, counted sequences, and sequences with custom start and step values.\n */\nexport interface Iterate {\n (): Iterable<number, void, unknown>;\n (count: number): Iterable<number, void, unknown>;\n (start: number, count: number): Iterable<number, void, unknown>;\n (start: number, count: number, step: number): Iterable<number, void, unknown>;\n}\n\n/**\n * Creates an iterable sequence of numbers with flexible parameters.\n * Can generate infinite sequences, finite sequences, or sequences with custom start and step values.\n *\n * @param args Variable arguments to configure the sequence:\n * - No args: Infinite sequence starting at 0 with step 1\n * - 1 arg (count): Sequence from 0 to count-1\n * - 2 args (start, count): Sequence starting at 'start' for 'count' iterations\n * - 3 args (start, count, step): Custom start, count, and step value\n * @returns An iterable that generates numbers according to the parameters\n *\n * @example\n * ```typescript\n * // Infinite sequence: 0, 1, 2, 3, ...\n * for (const n of iterate()) { }\n *\n * // Count only: 0, 1, 2, 3, 4\n * for (const n of iterate(5)) { }\n *\n * // Start and count: 10, 11, 12, 13, 14\n * for (const n of iterate(10, 5)) { }\n *\n * // Start, count, and step: 0, 2, 4, 6, 8\n * for (const n of iterate(0, 5, 2)) { }\n * ```\n */\nexport const iterate: Iterate = (startOrCount?: number, countWhenTwoArgs?: number, step: number = 1): Iterable<number, void, unknown> => {\n const hasStartArg = countWhenTwoArgs !== undefined;\n const start = hasStartArg ? startOrCount! : 0;\n const count = startOrCount === undefined ? Infinity : hasStartArg ? countWhenTwoArgs : startOrCount;\n\n return {\n [Symbol.iterator]() {\n let idx = 0;\n let current = start;\n return {\n next() {\n if (idx < count) {\n const value = current;\n current += step;\n idx++;\n return { value, done: false };\n }\n return ITERATOR_DONE;\n },\n return(value) {\n idx = count;\n return { value, done: true };\n },\n throw(error?: unknown) {\n idx = count;\n throw error;\n },\n } satisfies Iterator<number, void, unknown>;\n },\n };\n};\n\n/**\n * @internal\n * Creates a promise that resolves after a specified timeout. If an `AbortSignal` is provided and triggered,\n * the timeout is cleared, and the promise resolves to `false`.\n *\n * @param {number} timeout - The time in milliseconds to wait before resolving the promise.\n * @param {AbortSignal} [signal] - An optional `AbortSignal` that can abort the timeout.\n * @returns {Promise<boolean>} A promise that resolves to `true` if the timeout completed, or `false` if it was aborted.\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * setTimeout(() => controller.abort(), 500);\n * const result = await setTimeoutAsync(1000, controller.signal);\n * console.log(result); // false\n * ```\n */\nexport const setTimeoutAsync = async (timeout: number, signal?: AbortSignal): Promise<boolean> => {\n if (signal?.aborted) {\n return false;\n }\n const { promise, resolve } = Promise.withResolvers<boolean>();\n const timerId = setTimeout(resolve, timeout, true);\n const onAbort = () => {\n clearTimeout(timerId);\n resolve(false);\n };\n signal?.addEventListener('abort', onAbort);\n\n return promise.finally(() => signal?.removeEventListener('abort', onAbort));\n};\n\n/**\n * Converts a synchronous iterable to an asynchronous iterable.\n * Wraps the sync iterator methods to return promises, enabling uniform async handling.\n *\n * @template T The type of values yielded by the iterator\n * @template TReturn The return type of the iterator\n * @template TNext The type of value that can be passed to next()\n * @param iterable A synchronous iterable to convert\n * @returns An async iterable that yields the same values as the input\n *\n * @example\n * ```typescript\n * const syncArray = [1, 2, 3, 4, 5];\n * const asyncIterable = toAsyncIterable(syncArray);\n *\n * for await (const value of asyncIterable) {\n * console.log(value); // 1, 2, 3, 4, 5\n * }\n * ```\n */\nexport const toAsyncIterable = <T, TReturn, TNext>(iterable: Iterable<T, TReturn, TNext>): AsyncIterable<T, TReturn, TNext> => {\n return {\n [Symbol.asyncIterator]() {\n const iterator = iterable[Symbol.iterator]();\n return {\n next(...args: [TNext] | []) {\n return Promise.resolve(iterator.next(...args));\n },\n return(maybeValue) {\n return Promise.resolve(maybeValue).then((value) => iterator.return?.(value) ?? ({ value, done: true } as IteratorResult<T, TReturn>));\n },\n throw(error) {\n if (iterator.throw) {\n return Promise.resolve(iterator.throw(error));\n }\n return Promise.reject(error);\n },\n } satisfies AsyncIterator<T, TReturn, TNext>;\n },\n };\n};\n\n/**\n * @internal\n * Pipes values from an async iterable through a generator transformation.\n * Applies a generator function to each value, yielding all resulting values.\n * Supports cancellation via AbortSignal for early termination.\n *\n * @template T The input value type\n * @template U The output value type\n * @param iterable The source async iterable\n * @param generatorFactory A factory that returns a generator function for transforming values\n * @param signal Optional AbortSignal to cancel the operation\n * @returns An async generator yielding transformed values\n *\n * @example\n * ```typescript\n * async function* source() {\n * yield 1; yield 2; yield 3;\n * }\n *\n * const doubled = pipe(source(), () => async function*(n) {\n * yield n * 2;\n * });\n *\n * for await (const value of doubled) {\n * console.log(value); // 2, 4, 6\n * }\n * ```\n */\nconst isAsyncIterable = <T, TReturn, TNext>(value: AnyIterable<T, TReturn, TNext>): value is AsyncIterable<T, TReturn, TNext> => {\n return typeof (value as AsyncIterable<T, TReturn, TNext>)[Symbol.asyncIterator] === 'function';\n};\n\n/**\n * @internal\n */\nexport async function* pipe<T, U>(\n iterable: AsyncIterable<T>,\n generatorFactory: () => (value: T) => AnyIterable<U, void, unknown>,\n signal?: AbortSignal,\n): AsyncGenerator<Awaited<U>, void, unknown> {\n const source = signal ? abortableIterable(iterable, signal) : iterable;\n const generator = generatorFactory();\n\n for await (const value of source) {\n const produced = generator(value);\n const subIterable = isAsyncIterable(produced) ? produced : toAsyncIterable(produced);\n const abortableSub = signal ? abortableIterable(subIterable, signal) : subIterable;\n\n for await (const subValue of abortableSub) {\n yield subValue;\n }\n }\n}\n\n/**\n * @internal\n * Merges multiple async iterables into a single stream.\n * Values are yielded as they become available from any source.\n * Completes when all sources complete; aborts all on error.\n * @template T - The value type yielded by all iterables\n * @param iterables - The async iterables to merge\n * @returns A merged async iterable\n */\nexport const mergeIterables = <T>(...iterables: AsyncIterable<T, void, unknown>[]): AsyncIterable<T, void, unknown> => {\n return {\n [Symbol.asyncIterator]() {\n if (iterables.length === 0) {\n return {\n next: () => Promise.resolve(ITERATOR_DONE),\n };\n }\n\n const exit = Symbol('mergeIterables.exit');\n const ctrl = new AbortController();\n const sequence = new Sequence<T>(ctrl.signal);\n let remaining = iterables.length;\n\n const pump = async (iterable: AsyncIterable<T, void, unknown>) => {\n try {\n for await (const value of abortableIterable(iterable, ctrl.signal)) {\n if (!sequence.emit(value)) {\n break;\n }\n }\n } catch (error) {\n ctrl.abort(error);\n } finally {\n remaining -= 1;\n if (remaining === 0 && !ctrl.signal.aborted) {\n ctrl.abort(exit);\n }\n }\n };\n\n for (const iterable of iterables) {\n void pump(iterable);\n }\n\n return {\n next: async () => {\n try {\n const value = await sequence.receive();\n return { value, done: false };\n } catch {\n if (ctrl.signal.aborted && ctrl.signal.reason === exit) {\n return ITERATOR_DONE;\n }\n throw ctrl.signal.reason;\n }\n },\n return: async () => {\n ctrl.abort(exit);\n return ITERATOR_DONE;\n },\n throw: async (error?: unknown) => {\n ctrl.abort(error);\n return ITERATOR_DONE;\n },\n };\n },\n };\n};\n"],"names":["MapIteratorType","abortableIterable","isThenable","iterate","mapIterator","mergeIterables","min","noop","pipe","setTimeoutAsync","toAsyncIterable","value","then","values","fallback","result","Infinity","iterator","map","subIterator","next","args","return","done","throw","iterable","signal","Symbol","asyncIterator","promise","resolve","Promise","withResolvers","onAbort","closed","finish","removeEventListener","aborted","addEventListener","race","undefined","startOrCount","countWhenTwoArgs","step","hasStartArg","start","count","idx","current","ITERATOR_DONE","error","timeout","timerId","setTimeout","clearTimeout","finally","maybeValue","reject","isAsyncIterable","generatorFactory","source","generator","produced","subIterable","abortableSub","subValue","iterables","length","exit","ctrl","AbortController","sequence","Sequence","remaining","pump","emit","abort","receive","reason"],"mappings":"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"}
|
package/build/utils.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { Sequence } from "./sequence.js";
|
|
2
|
+
import { ITERATOR_DONE } from "./async.js";
|
|
2
3
|
export function isThenable(value) {
|
|
3
4
|
return value !== null && typeof value === 'object' && typeof value.then === 'function';
|
|
4
5
|
}
|
|
@@ -75,23 +76,24 @@ export function abortableIterable(iterable, signal) {
|
|
|
75
76
|
undefined
|
|
76
77
|
];
|
|
77
78
|
return {
|
|
78
|
-
|
|
79
|
+
next (...args) {
|
|
79
80
|
race[1] = iterator.next(...args);
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
81
|
+
return Promise.race(race).then((result)=>{
|
|
82
|
+
if (result === undefined) {
|
|
83
|
+
void finish();
|
|
84
|
+
return {
|
|
85
|
+
done: true,
|
|
86
|
+
value: undefined
|
|
87
|
+
};
|
|
88
|
+
}
|
|
89
|
+
if (result.done) {
|
|
90
|
+
closed = true;
|
|
91
|
+
signal.removeEventListener('abort', onAbort);
|
|
92
|
+
}
|
|
93
|
+
return result;
|
|
94
|
+
});
|
|
93
95
|
},
|
|
94
|
-
|
|
96
|
+
return (value) {
|
|
95
97
|
return finish(value);
|
|
96
98
|
}
|
|
97
99
|
};
|
|
@@ -117,10 +119,7 @@ export const iterate = (startOrCount, countWhenTwoArgs, step = 1)=>{
|
|
|
117
119
|
done: false
|
|
118
120
|
};
|
|
119
121
|
}
|
|
120
|
-
return
|
|
121
|
-
value: undefined,
|
|
122
|
-
done: true
|
|
123
|
-
};
|
|
122
|
+
return ITERATOR_DONE;
|
|
124
123
|
},
|
|
125
124
|
return (value) {
|
|
126
125
|
idx = count;
|
|
@@ -155,21 +154,20 @@ export const toAsyncIterable = (iterable)=>{
|
|
|
155
154
|
[Symbol.asyncIterator] () {
|
|
156
155
|
const iterator = iterable[Symbol.iterator]();
|
|
157
156
|
return {
|
|
158
|
-
|
|
159
|
-
return iterator.next(...args);
|
|
157
|
+
next (...args) {
|
|
158
|
+
return Promise.resolve(iterator.next(...args));
|
|
160
159
|
},
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
};
|
|
160
|
+
return (maybeValue) {
|
|
161
|
+
return Promise.resolve(maybeValue).then((value)=>iterator.return?.(value) ?? {
|
|
162
|
+
value,
|
|
163
|
+
done: true
|
|
164
|
+
});
|
|
167
165
|
},
|
|
168
|
-
|
|
166
|
+
throw (error) {
|
|
169
167
|
if (iterator.throw) {
|
|
170
|
-
return iterator.throw(error);
|
|
168
|
+
return Promise.resolve(iterator.throw(error));
|
|
171
169
|
}
|
|
172
|
-
|
|
170
|
+
return Promise.reject(error);
|
|
173
171
|
}
|
|
174
172
|
};
|
|
175
173
|
}
|
|
@@ -195,10 +193,7 @@ export const mergeIterables = (...iterables)=>{
|
|
|
195
193
|
[Symbol.asyncIterator] () {
|
|
196
194
|
if (iterables.length === 0) {
|
|
197
195
|
return {
|
|
198
|
-
next:
|
|
199
|
-
value: undefined,
|
|
200
|
-
done: true
|
|
201
|
-
})
|
|
196
|
+
next: ()=>Promise.resolve(ITERATOR_DONE)
|
|
202
197
|
};
|
|
203
198
|
}
|
|
204
199
|
const exit = Symbol('mergeIterables.exit');
|
|
@@ -234,27 +229,18 @@ export const mergeIterables = (...iterables)=>{
|
|
|
234
229
|
};
|
|
235
230
|
} catch {
|
|
236
231
|
if (ctrl.signal.aborted && ctrl.signal.reason === exit) {
|
|
237
|
-
return
|
|
238
|
-
value: undefined,
|
|
239
|
-
done: true
|
|
240
|
-
};
|
|
232
|
+
return ITERATOR_DONE;
|
|
241
233
|
}
|
|
242
234
|
throw ctrl.signal.reason;
|
|
243
235
|
}
|
|
244
236
|
},
|
|
245
237
|
return: async ()=>{
|
|
246
238
|
ctrl.abort(exit);
|
|
247
|
-
return
|
|
248
|
-
value: undefined,
|
|
249
|
-
done: true
|
|
250
|
-
};
|
|
239
|
+
return ITERATOR_DONE;
|
|
251
240
|
},
|
|
252
241
|
throw: async (error)=>{
|
|
253
242
|
ctrl.abort(error);
|
|
254
|
-
return
|
|
255
|
-
value: undefined,
|
|
256
|
-
done: true
|
|
257
|
-
};
|
|
243
|
+
return ITERATOR_DONE;
|
|
258
244
|
}
|
|
259
245
|
};
|
|
260
246
|
}
|
package/build/utils.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/utils.ts"],"sourcesContent":["import { Sequence } from './sequence.js';\nimport { AnyIterator, AnyIterable, MaybePromise } from './types.js';\n\n/**\n * @internal\n */\nexport function isThenable(value: unknown): value is PromiseLike<unknown> {\n return value !== null && typeof value === 'object' && typeof (value as PromiseLike<unknown>).then === 'function';\n}\n\n/**\n * @internal\n * A no-operation function. Useful as a default callback or placeholder.\n */\nexport const noop = () => {};\n\n/**\n * @internal\n * Returns the minimum value from an iterable, or a fallback if empty.\n */\nexport function min(values: Iterable<number>, fallback: number): number {\n let result = Infinity;\n for (const value of values) {\n if (value < result) result = value;\n }\n return result === Infinity ? fallback : result;\n}\n\n/**\n * @internal\n * Indicates which iterator method triggered a mapping operation.\n */\nexport enum MapIteratorType {\n /** The next() method was called */\n NEXT,\n /** The return() method was called */\n RETURN,\n /** The throw() method was called */\n THROW,\n}\n\n/**\n * @internal\n * A mapping function for transforming iterator results.\n * @template T - The input value type\n * @template U - The output value type\n * @template TReturn - The iterator return type\n */\nexport interface MapNext<T, U, TReturn> {\n (result: MaybePromise<IteratorResult<T, TReturn>>, type: MapIteratorType): MaybePromise<IteratorResult<U, TReturn>>;\n}\n\n/**\n * @internal\n * Wraps an iterator with a mapping function applied to each result.\n * @template U - The output value type\n * @template T - The input value type\n * @template TReturn - The iterator return type\n * @template TNext - The type passed to next()\n * @param iterator - The source iterator to wrap\n * @param map - The mapping function to apply to each result\n * @returns An async iterator with mapped results\n */\nexport const mapIterator = <U, T, TReturn, TNext>(iterator: AnyIterator<T, TReturn, TNext>, map: MapNext<T, U, TReturn>): AsyncIterator<U, TReturn, TNext> => {\n const subIterator: AsyncIterator<U, TReturn, TNext> = {\n next: async (...args: [] | [TNext]) => {\n const result = await iterator.next(...args);\n return map(result, MapIteratorType.NEXT);\n },\n };\n if (iterator.return) {\n subIterator.return = async (...args: [] | [TReturn]) => {\n const result = await iterator.return!(...args);\n return map(result, MapIteratorType.RETURN);\n };\n } else {\n subIterator.return = async (value: TReturn) => {\n return map({ done: true, value }, MapIteratorType.RETURN);\n };\n }\n if (iterator.throw) {\n subIterator.throw = async (...args: [] | [unknown]) => {\n const result = await iterator.throw!(...args);\n return map(result, MapIteratorType.THROW);\n };\n }\n\n return subIterator;\n};\n\n/**\n * Wraps an async iterable with abort signal support.\n * Each iteration creates a fresh iterator with scoped abort handling.\n * Listener is added at iteration start and removed on completion/abort/return.\n *\n * @template T - The yielded value type\n * @template TReturn - The return value type\n * @template TNext - The type passed to next()\n * @param iterable - The source async iterable to wrap\n * @param signal - AbortSignal to cancel iteration\n * @returns An async iterable with abort support\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * const source = async function*() { yield 1; yield 2; yield 3; };\n *\n * for await (const value of abortableIterable(source(), controller.signal)) {\n * console.log(value);\n * if (value === 2) controller.abort();\n * }\n * ```\n */\nexport function abortableIterable<T, TReturn, TNext>(iterable: AsyncIterable<T, TReturn, TNext>, signal: AbortSignal): AsyncIterable<T, TReturn, TNext> {\n return {\n [Symbol.asyncIterator](): AsyncIterator<T, TReturn, TNext> {\n const iterator = iterable[Symbol.asyncIterator]();\n const { promise, resolve } = Promise.withResolvers<void>();\n const onAbort = () => resolve();\n let closed = false;\n\n const finish = (value?: TReturn): Promise<IteratorResult<T, TReturn>> => {\n if (closed) {\n return Promise.resolve({ done: true, value: value as TReturn });\n }\n closed = true;\n signal.removeEventListener('abort', onAbort);\n return iterator.return?.(value) ?? Promise.resolve({ done: true, value: value as TReturn });\n };\n\n if (signal.aborted) {\n onAbort();\n } else {\n signal.addEventListener('abort', onAbort);\n }\n\n const race = [promise, undefined] as unknown as [Promise<void>, Promise<IteratorResult<T, TReturn>>];\n\n return {\n async next(...args: [] | [TNext]): Promise<IteratorResult<T, TReturn>> {\n race[1] = iterator.next(...args);\n const result = await Promise.race(race);\n if (result === undefined) {\n void finish();\n return { done: true, value: undefined as TReturn };\n }\n if (result.done) {\n closed = true;\n signal.removeEventListener('abort', onAbort);\n }\n return result;\n },\n async return(value?: TReturn): Promise<IteratorResult<T, TReturn>> {\n return finish(value);\n },\n };\n },\n };\n}\n\n/**\n * Interface for creating iterable number sequences with various parameter combinations.\n * Supports infinite sequences, counted sequences, and sequences with custom start and step values.\n */\nexport interface Iterate {\n (): Iterable<number, void, unknown>;\n (count: number): Iterable<number, void, unknown>;\n (start: number, count: number): Iterable<number, void, unknown>;\n (start: number, count: number, step: number): Iterable<number, void, unknown>;\n}\n\n/**\n * Creates an iterable sequence of numbers with flexible parameters.\n * Can generate infinite sequences, finite sequences, or sequences with custom start and step values.\n *\n * @param args Variable arguments to configure the sequence:\n * - No args: Infinite sequence starting at 0 with step 1\n * - 1 arg (count): Sequence from 0 to count-1\n * - 2 args (start, count): Sequence starting at 'start' for 'count' iterations\n * - 3 args (start, count, step): Custom start, count, and step value\n * @returns An iterable that generates numbers according to the parameters\n *\n * @example\n * ```typescript\n * // Infinite sequence: 0, 1, 2, 3, ...\n * for (const n of iterate()) { }\n *\n * // Count only: 0, 1, 2, 3, 4\n * for (const n of iterate(5)) { }\n *\n * // Start and count: 10, 11, 12, 13, 14\n * for (const n of iterate(10, 5)) { }\n *\n * // Start, count, and step: 0, 2, 4, 6, 8\n * for (const n of iterate(0, 5, 2)) { }\n * ```\n */\nexport const iterate: Iterate = (startOrCount?: number, countWhenTwoArgs?: number, step: number = 1): Iterable<number, void, unknown> => {\n const hasStartArg = countWhenTwoArgs !== undefined;\n const start = hasStartArg ? startOrCount! : 0;\n const count = startOrCount === undefined ? Infinity : hasStartArg ? countWhenTwoArgs : startOrCount;\n\n return {\n [Symbol.iterator]() {\n let idx = 0;\n let current = start;\n return {\n next() {\n if (idx < count) {\n const value = current;\n current += step;\n idx++;\n return { value, done: false };\n }\n return { value: undefined, done: true };\n },\n return(value) {\n idx = count;\n return { value, done: true };\n },\n throw(error?: unknown) {\n idx = count;\n throw error;\n },\n } satisfies Iterator<number, void, unknown>;\n },\n };\n};\n\n/**\n * @internal\n * Creates a promise that resolves after a specified timeout. If an `AbortSignal` is provided and triggered,\n * the timeout is cleared, and the promise resolves to `false`.\n *\n * @param {number} timeout - The time in milliseconds to wait before resolving the promise.\n * @param {AbortSignal} [signal] - An optional `AbortSignal` that can abort the timeout.\n * @returns {Promise<boolean>} A promise that resolves to `true` if the timeout completed, or `false` if it was aborted.\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * setTimeout(() => controller.abort(), 500);\n * const result = await setTimeoutAsync(1000, controller.signal);\n * console.log(result); // false\n * ```\n */\nexport const setTimeoutAsync = async (timeout: number, signal?: AbortSignal): Promise<boolean> => {\n if (signal?.aborted) {\n return false;\n }\n const { promise, resolve } = Promise.withResolvers<boolean>();\n const timerId = setTimeout(resolve, timeout, true);\n const onAbort = () => {\n clearTimeout(timerId);\n resolve(false);\n };\n signal?.addEventListener('abort', onAbort);\n\n return promise.finally(() => signal?.removeEventListener('abort', onAbort));\n};\n\n/**\n * Converts a synchronous iterable to an asynchronous iterable.\n * Wraps the sync iterator methods to return promises, enabling uniform async handling.\n *\n * @template T The type of values yielded by the iterator\n * @template TReturn The return type of the iterator\n * @template TNext The type of value that can be passed to next()\n * @param iterable A synchronous iterable to convert\n * @returns An async iterable that yields the same values as the input\n *\n * @example\n * ```typescript\n * const syncArray = [1, 2, 3, 4, 5];\n * const asyncIterable = toAsyncIterable(syncArray);\n *\n * for await (const value of asyncIterable) {\n * console.log(value); // 1, 2, 3, 4, 5\n * }\n * ```\n */\nexport const toAsyncIterable = <T, TReturn, TNext>(iterable: Iterable<T, TReturn, TNext>): AsyncIterable<T, TReturn, TNext> => {\n return {\n [Symbol.asyncIterator]() {\n const iterator = iterable[Symbol.iterator]();\n return {\n async next(...args: [TNext] | []) {\n return iterator.next(...args);\n },\n async return(maybeValue) {\n const value = await maybeValue;\n return iterator.return?.(value) ?? ({ value, done: true } as IteratorResult<T, TReturn>);\n },\n async throw(error) {\n if (iterator.throw) {\n return iterator.throw(error);\n }\n throw error;\n },\n } satisfies AsyncIterator<T, TReturn, TNext>;\n },\n };\n};\n\n/**\n * @internal\n * Pipes values from an async iterable through a generator transformation.\n * Applies a generator function to each value, yielding all resulting values.\n * Supports cancellation via AbortSignal for early termination.\n *\n * @template T The input value type\n * @template U The output value type\n * @param iterable The source async iterable\n * @param generatorFactory A factory that returns a generator function for transforming values\n * @param signal Optional AbortSignal to cancel the operation\n * @returns An async generator yielding transformed values\n *\n * @example\n * ```typescript\n * async function* source() {\n * yield 1; yield 2; yield 3;\n * }\n *\n * const doubled = pipe(source(), () => async function*(n) {\n * yield n * 2;\n * });\n *\n * for await (const value of doubled) {\n * console.log(value); // 2, 4, 6\n * }\n * ```\n */\nconst isAsyncIterable = <T, TReturn, TNext>(value: AnyIterable<T, TReturn, TNext>): value is AsyncIterable<T, TReturn, TNext> => {\n return typeof (value as AsyncIterable<T, TReturn, TNext>)[Symbol.asyncIterator] === 'function';\n};\n\n/**\n * @internal\n */\nexport async function* pipe<T, U>(\n iterable: AsyncIterable<T>,\n generatorFactory: () => (value: T) => AnyIterable<U, void, unknown>,\n signal?: AbortSignal,\n): AsyncGenerator<Awaited<U>, void, unknown> {\n const source = signal ? abortableIterable(iterable, signal) : iterable;\n const generator = generatorFactory();\n\n for await (const value of source) {\n const produced = generator(value);\n const subIterable = isAsyncIterable(produced) ? produced : toAsyncIterable(produced);\n const abortableSub = signal ? abortableIterable(subIterable, signal) : subIterable;\n\n for await (const subValue of abortableSub) {\n yield subValue;\n }\n }\n}\n\n/**\n * @internal\n * Merges multiple async iterables into a single stream.\n * Values are yielded as they become available from any source.\n * Completes when all sources complete; aborts all on error.\n * @template T - The value type yielded by all iterables\n * @param iterables - The async iterables to merge\n * @returns A merged async iterable\n */\nexport const mergeIterables = <T>(...iterables: AsyncIterable<T, void, unknown>[]): AsyncIterable<T, void, unknown> => {\n return {\n [Symbol.asyncIterator]() {\n if (iterables.length === 0) {\n return {\n next: async () => ({ value: undefined, done: true }),\n };\n }\n\n const exit = Symbol('mergeIterables.exit');\n const ctrl = new AbortController();\n const sequence = new Sequence<T>(ctrl.signal);\n let remaining = iterables.length;\n\n const pump = async (iterable: AsyncIterable<T, void, unknown>) => {\n try {\n for await (const value of abortableIterable(iterable, ctrl.signal)) {\n if (!sequence.emit(value)) {\n break;\n }\n }\n } catch (error) {\n ctrl.abort(error);\n } finally {\n remaining -= 1;\n if (remaining === 0 && !ctrl.signal.aborted) {\n ctrl.abort(exit);\n }\n }\n };\n\n for (const iterable of iterables) {\n void pump(iterable);\n }\n\n return {\n next: async () => {\n try {\n const value = await sequence.receive();\n return { value, done: false };\n } catch {\n if (ctrl.signal.aborted && ctrl.signal.reason === exit) {\n return { value: undefined, done: true };\n }\n throw ctrl.signal.reason;\n }\n },\n return: async () => {\n ctrl.abort(exit);\n return { value: undefined, done: true };\n },\n throw: async (error?: unknown) => {\n ctrl.abort(error);\n return { value: undefined, done: true };\n },\n };\n },\n };\n};\n"],"names":["Sequence","isThenable","value","then","noop","min","values","fallback","result","Infinity","MapIteratorType","mapIterator","iterator","map","subIterator","next","args","return","done","throw","abortableIterable","iterable","signal","Symbol","asyncIterator","promise","resolve","Promise","withResolvers","onAbort","closed","finish","removeEventListener","aborted","addEventListener","race","undefined","iterate","startOrCount","countWhenTwoArgs","step","hasStartArg","start","count","idx","current","error","setTimeoutAsync","timeout","timerId","setTimeout","clearTimeout","finally","toAsyncIterable","maybeValue","isAsyncIterable","pipe","generatorFactory","source","generator","produced","subIterable","abortableSub","subValue","mergeIterables","iterables","length","exit","ctrl","AbortController","sequence","remaining","pump","emit","abort","receive","reason"],"mappings":"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"}
|
|
1
|
+
{"version":3,"sources":["../src/utils.ts"],"sourcesContent":["import { Sequence } from './sequence.js';\nimport { ITERATOR_DONE } from './async.js';\nimport { AnyIterator, AnyIterable, MaybePromise } from './types.js';\n\n/**\n * @internal\n */\nexport function isThenable(value: unknown): value is PromiseLike<unknown> {\n return value !== null && typeof value === 'object' && typeof (value as PromiseLike<unknown>).then === 'function';\n}\n\n/**\n * @internal\n * A no-operation function. Useful as a default callback or placeholder.\n */\nexport const noop = () => {};\n\n/**\n * @internal\n * Returns the minimum value from an iterable, or a fallback if empty.\n */\nexport function min(values: Iterable<number>, fallback: number): number {\n let result = Infinity;\n for (const value of values) {\n if (value < result) result = value;\n }\n return result === Infinity ? fallback : result;\n}\n\n/**\n * @internal\n * Indicates which iterator method triggered a mapping operation.\n */\nexport enum MapIteratorType {\n /** The next() method was called */\n NEXT,\n /** The return() method was called */\n RETURN,\n /** The throw() method was called */\n THROW,\n}\n\n/**\n * @internal\n * A mapping function for transforming iterator results.\n * @template T - The input value type\n * @template U - The output value type\n * @template TReturn - The iterator return type\n */\nexport interface MapNext<T, U, TReturn> {\n (result: MaybePromise<IteratorResult<T, TReturn>>, type: MapIteratorType): MaybePromise<IteratorResult<U, TReturn>>;\n}\n\n/**\n * @internal\n * Wraps an iterator with a mapping function applied to each result.\n * @template U - The output value type\n * @template T - The input value type\n * @template TReturn - The iterator return type\n * @template TNext - The type passed to next()\n * @param iterator - The source iterator to wrap\n * @param map - The mapping function to apply to each result\n * @returns An async iterator with mapped results\n */\nexport const mapIterator = <U, T, TReturn, TNext>(iterator: AnyIterator<T, TReturn, TNext>, map: MapNext<T, U, TReturn>): AsyncIterator<U, TReturn, TNext> => {\n const subIterator: AsyncIterator<U, TReturn, TNext> = {\n next: async (...args: [] | [TNext]) => {\n const result = await iterator.next(...args);\n return map(result, MapIteratorType.NEXT);\n },\n };\n if (iterator.return) {\n subIterator.return = async (...args: [] | [TReturn]) => {\n const result = await iterator.return!(...args);\n return map(result, MapIteratorType.RETURN);\n };\n } else {\n subIterator.return = async (value: TReturn) => {\n return map({ done: true, value }, MapIteratorType.RETURN);\n };\n }\n if (iterator.throw) {\n subIterator.throw = async (...args: [] | [unknown]) => {\n const result = await iterator.throw!(...args);\n return map(result, MapIteratorType.THROW);\n };\n }\n\n return subIterator;\n};\n\n/**\n * Wraps an async iterable with abort signal support.\n * Each iteration creates a fresh iterator with scoped abort handling.\n * Listener is added at iteration start and removed on completion/abort/return.\n *\n * @template T - The yielded value type\n * @template TReturn - The return value type\n * @template TNext - The type passed to next()\n * @param iterable - The source async iterable to wrap\n * @param signal - AbortSignal to cancel iteration\n * @returns An async iterable with abort support\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * const source = async function*() { yield 1; yield 2; yield 3; };\n *\n * for await (const value of abortableIterable(source(), controller.signal)) {\n * console.log(value);\n * if (value === 2) controller.abort();\n * }\n * ```\n */\nexport function abortableIterable<T, TReturn, TNext>(iterable: AsyncIterable<T, TReturn, TNext>, signal: AbortSignal): AsyncIterable<T, TReturn, TNext> {\n return {\n [Symbol.asyncIterator](): AsyncIterator<T, TReturn, TNext> {\n const iterator = iterable[Symbol.asyncIterator]();\n const { promise, resolve } = Promise.withResolvers<void>();\n const onAbort = () => resolve();\n let closed = false;\n\n const finish = (value?: TReturn): Promise<IteratorResult<T, TReturn>> => {\n if (closed) {\n return Promise.resolve({ done: true, value: value as TReturn });\n }\n closed = true;\n signal.removeEventListener('abort', onAbort);\n return iterator.return?.(value) ?? Promise.resolve({ done: true, value: value as TReturn });\n };\n\n if (signal.aborted) {\n onAbort();\n } else {\n signal.addEventListener('abort', onAbort);\n }\n\n const race = [promise, undefined] as unknown as [Promise<void>, Promise<IteratorResult<T, TReturn>>];\n\n return {\n next(...args: [] | [TNext]): Promise<IteratorResult<T, TReturn>> {\n race[1] = iterator.next(...args);\n return Promise.race(race).then((result) => {\n if (result === undefined) {\n void finish();\n return { done: true, value: undefined as TReturn } as IteratorResult<T, TReturn>;\n }\n if (result.done) {\n closed = true;\n signal.removeEventListener('abort', onAbort);\n }\n return result;\n });\n },\n return(value?: TReturn): Promise<IteratorResult<T, TReturn>> {\n return finish(value);\n },\n };\n },\n };\n}\n\n/**\n * Interface for creating iterable number sequences with various parameter combinations.\n * Supports infinite sequences, counted sequences, and sequences with custom start and step values.\n */\nexport interface Iterate {\n (): Iterable<number, void, unknown>;\n (count: number): Iterable<number, void, unknown>;\n (start: number, count: number): Iterable<number, void, unknown>;\n (start: number, count: number, step: number): Iterable<number, void, unknown>;\n}\n\n/**\n * Creates an iterable sequence of numbers with flexible parameters.\n * Can generate infinite sequences, finite sequences, or sequences with custom start and step values.\n *\n * @param args Variable arguments to configure the sequence:\n * - No args: Infinite sequence starting at 0 with step 1\n * - 1 arg (count): Sequence from 0 to count-1\n * - 2 args (start, count): Sequence starting at 'start' for 'count' iterations\n * - 3 args (start, count, step): Custom start, count, and step value\n * @returns An iterable that generates numbers according to the parameters\n *\n * @example\n * ```typescript\n * // Infinite sequence: 0, 1, 2, 3, ...\n * for (const n of iterate()) { }\n *\n * // Count only: 0, 1, 2, 3, 4\n * for (const n of iterate(5)) { }\n *\n * // Start and count: 10, 11, 12, 13, 14\n * for (const n of iterate(10, 5)) { }\n *\n * // Start, count, and step: 0, 2, 4, 6, 8\n * for (const n of iterate(0, 5, 2)) { }\n * ```\n */\nexport const iterate: Iterate = (startOrCount?: number, countWhenTwoArgs?: number, step: number = 1): Iterable<number, void, unknown> => {\n const hasStartArg = countWhenTwoArgs !== undefined;\n const start = hasStartArg ? startOrCount! : 0;\n const count = startOrCount === undefined ? Infinity : hasStartArg ? countWhenTwoArgs : startOrCount;\n\n return {\n [Symbol.iterator]() {\n let idx = 0;\n let current = start;\n return {\n next() {\n if (idx < count) {\n const value = current;\n current += step;\n idx++;\n return { value, done: false };\n }\n return ITERATOR_DONE;\n },\n return(value) {\n idx = count;\n return { value, done: true };\n },\n throw(error?: unknown) {\n idx = count;\n throw error;\n },\n } satisfies Iterator<number, void, unknown>;\n },\n };\n};\n\n/**\n * @internal\n * Creates a promise that resolves after a specified timeout. If an `AbortSignal` is provided and triggered,\n * the timeout is cleared, and the promise resolves to `false`.\n *\n * @param {number} timeout - The time in milliseconds to wait before resolving the promise.\n * @param {AbortSignal} [signal] - An optional `AbortSignal` that can abort the timeout.\n * @returns {Promise<boolean>} A promise that resolves to `true` if the timeout completed, or `false` if it was aborted.\n *\n * @example\n * ```typescript\n * const controller = new AbortController();\n * setTimeout(() => controller.abort(), 500);\n * const result = await setTimeoutAsync(1000, controller.signal);\n * console.log(result); // false\n * ```\n */\nexport const setTimeoutAsync = async (timeout: number, signal?: AbortSignal): Promise<boolean> => {\n if (signal?.aborted) {\n return false;\n }\n const { promise, resolve } = Promise.withResolvers<boolean>();\n const timerId = setTimeout(resolve, timeout, true);\n const onAbort = () => {\n clearTimeout(timerId);\n resolve(false);\n };\n signal?.addEventListener('abort', onAbort);\n\n return promise.finally(() => signal?.removeEventListener('abort', onAbort));\n};\n\n/**\n * Converts a synchronous iterable to an asynchronous iterable.\n * Wraps the sync iterator methods to return promises, enabling uniform async handling.\n *\n * @template T The type of values yielded by the iterator\n * @template TReturn The return type of the iterator\n * @template TNext The type of value that can be passed to next()\n * @param iterable A synchronous iterable to convert\n * @returns An async iterable that yields the same values as the input\n *\n * @example\n * ```typescript\n * const syncArray = [1, 2, 3, 4, 5];\n * const asyncIterable = toAsyncIterable(syncArray);\n *\n * for await (const value of asyncIterable) {\n * console.log(value); // 1, 2, 3, 4, 5\n * }\n * ```\n */\nexport const toAsyncIterable = <T, TReturn, TNext>(iterable: Iterable<T, TReturn, TNext>): AsyncIterable<T, TReturn, TNext> => {\n return {\n [Symbol.asyncIterator]() {\n const iterator = iterable[Symbol.iterator]();\n return {\n next(...args: [TNext] | []) {\n return Promise.resolve(iterator.next(...args));\n },\n return(maybeValue) {\n return Promise.resolve(maybeValue).then((value) => iterator.return?.(value) ?? ({ value, done: true } as IteratorResult<T, TReturn>));\n },\n throw(error) {\n if (iterator.throw) {\n return Promise.resolve(iterator.throw(error));\n }\n return Promise.reject(error);\n },\n } satisfies AsyncIterator<T, TReturn, TNext>;\n },\n };\n};\n\n/**\n * @internal\n * Pipes values from an async iterable through a generator transformation.\n * Applies a generator function to each value, yielding all resulting values.\n * Supports cancellation via AbortSignal for early termination.\n *\n * @template T The input value type\n * @template U The output value type\n * @param iterable The source async iterable\n * @param generatorFactory A factory that returns a generator function for transforming values\n * @param signal Optional AbortSignal to cancel the operation\n * @returns An async generator yielding transformed values\n *\n * @example\n * ```typescript\n * async function* source() {\n * yield 1; yield 2; yield 3;\n * }\n *\n * const doubled = pipe(source(), () => async function*(n) {\n * yield n * 2;\n * });\n *\n * for await (const value of doubled) {\n * console.log(value); // 2, 4, 6\n * }\n * ```\n */\nconst isAsyncIterable = <T, TReturn, TNext>(value: AnyIterable<T, TReturn, TNext>): value is AsyncIterable<T, TReturn, TNext> => {\n return typeof (value as AsyncIterable<T, TReturn, TNext>)[Symbol.asyncIterator] === 'function';\n};\n\n/**\n * @internal\n */\nexport async function* pipe<T, U>(\n iterable: AsyncIterable<T>,\n generatorFactory: () => (value: T) => AnyIterable<U, void, unknown>,\n signal?: AbortSignal,\n): AsyncGenerator<Awaited<U>, void, unknown> {\n const source = signal ? abortableIterable(iterable, signal) : iterable;\n const generator = generatorFactory();\n\n for await (const value of source) {\n const produced = generator(value);\n const subIterable = isAsyncIterable(produced) ? produced : toAsyncIterable(produced);\n const abortableSub = signal ? abortableIterable(subIterable, signal) : subIterable;\n\n for await (const subValue of abortableSub) {\n yield subValue;\n }\n }\n}\n\n/**\n * @internal\n * Merges multiple async iterables into a single stream.\n * Values are yielded as they become available from any source.\n * Completes when all sources complete; aborts all on error.\n * @template T - The value type yielded by all iterables\n * @param iterables - The async iterables to merge\n * @returns A merged async iterable\n */\nexport const mergeIterables = <T>(...iterables: AsyncIterable<T, void, unknown>[]): AsyncIterable<T, void, unknown> => {\n return {\n [Symbol.asyncIterator]() {\n if (iterables.length === 0) {\n return {\n next: () => Promise.resolve(ITERATOR_DONE),\n };\n }\n\n const exit = Symbol('mergeIterables.exit');\n const ctrl = new AbortController();\n const sequence = new Sequence<T>(ctrl.signal);\n let remaining = iterables.length;\n\n const pump = async (iterable: AsyncIterable<T, void, unknown>) => {\n try {\n for await (const value of abortableIterable(iterable, ctrl.signal)) {\n if (!sequence.emit(value)) {\n break;\n }\n }\n } catch (error) {\n ctrl.abort(error);\n } finally {\n remaining -= 1;\n if (remaining === 0 && !ctrl.signal.aborted) {\n ctrl.abort(exit);\n }\n }\n };\n\n for (const iterable of iterables) {\n void pump(iterable);\n }\n\n return {\n next: async () => {\n try {\n const value = await sequence.receive();\n return { value, done: false };\n } catch {\n if (ctrl.signal.aborted && ctrl.signal.reason === exit) {\n return ITERATOR_DONE;\n }\n throw ctrl.signal.reason;\n }\n },\n return: async () => {\n ctrl.abort(exit);\n return ITERATOR_DONE;\n },\n throw: async (error?: unknown) => {\n ctrl.abort(error);\n return ITERATOR_DONE;\n },\n };\n },\n };\n};\n"],"names":["Sequence","ITERATOR_DONE","isThenable","value","then","noop","min","values","fallback","result","Infinity","MapIteratorType","mapIterator","iterator","map","subIterator","next","args","return","done","throw","abortableIterable","iterable","signal","Symbol","asyncIterator","promise","resolve","Promise","withResolvers","onAbort","closed","finish","removeEventListener","aborted","addEventListener","race","undefined","iterate","startOrCount","countWhenTwoArgs","step","hasStartArg","start","count","idx","current","error","setTimeoutAsync","timeout","timerId","setTimeout","clearTimeout","finally","toAsyncIterable","maybeValue","reject","isAsyncIterable","pipe","generatorFactory","source","generator","produced","subIterable","abortableSub","subValue","mergeIterables","iterables","length","exit","ctrl","AbortController","sequence","remaining","pump","emit","abort","receive","reason"],"mappings":"AAAA,SAASA,QAAQ,QAAQ,gBAAgB;AACzC,SAASC,aAAa,QAAQ,aAAa;AAM3C,OAAO,SAASC,WAAWC,KAAc;IACvC,OAAOA,UAAU,QAAQ,OAAOA,UAAU,YAAY,OAAO,AAACA,MAA+BC,IAAI,KAAK;AACxG;AAMA,OAAO,MAAMC,OAAO,KAAO,EAAE;AAM7B,OAAO,SAASC,IAAIC,MAAwB,EAAEC,QAAgB;IAC5D,IAAIC,SAASC;IACb,KAAK,MAAMP,SAASI,OAAQ;QAC1B,IAAIJ,QAAQM,QAAQA,SAASN;IAC/B;IACA,OAAOM,WAAWC,WAAWF,WAAWC;AAC1C;AAMA,OAAO,IAAA,AAAKE,yCAAAA;;;;WAAAA;MAOX;AAwBD,OAAO,MAAMC,cAAc,CAAuBC,UAA0CC;IAC1F,MAAMC,cAAgD;QACpDC,MAAM,OAAO,GAAGC;YACd,MAAMR,SAAS,MAAMI,SAASG,IAAI,IAAIC;YACtC,OAAOH,IAAIL;QACb;IACF;IACA,IAAII,SAASK,MAAM,EAAE;QACnBH,YAAYG,MAAM,GAAG,OAAO,GAAGD;YAC7B,MAAMR,SAAS,MAAMI,SAASK,MAAM,IAAKD;YACzC,OAAOH,IAAIL;QACb;IACF,OAAO;QACLM,YAAYG,MAAM,GAAG,OAAOf;YAC1B,OAAOW,IAAI;gBAAEK,MAAM;gBAAMhB;YAAM;QACjC;IACF;IACA,IAAIU,SAASO,KAAK,EAAE;QAClBL,YAAYK,KAAK,GAAG,OAAO,GAAGH;YAC5B,MAAMR,SAAS,MAAMI,SAASO,KAAK,IAAKH;YACxC,OAAOH,IAAIL;QACb;IACF;IAEA,OAAOM;AACT,EAAE;AAyBF,OAAO,SAASM,kBAAqCC,QAA0C,EAAEC,MAAmB;IAClH,OAAO;QACL,CAACC,OAAOC,aAAa,CAAC;YACpB,MAAMZ,WAAWS,QAAQ,CAACE,OAAOC,aAAa,CAAC;YAC/C,MAAM,EAAEC,OAAO,EAAEC,OAAO,EAAE,GAAGC,QAAQC,aAAa;YAClD,MAAMC,UAAU,IAAMH;YACtB,IAAII,SAAS;YAEb,MAAMC,SAAS,CAAC7B;gBACd,IAAI4B,QAAQ;oBACV,OAAOH,QAAQD,OAAO,CAAC;wBAAER,MAAM;wBAAMhB,OAAOA;oBAAiB;gBAC/D;gBACA4B,SAAS;gBACTR,OAAOU,mBAAmB,CAAC,SAASH;gBACpC,OAAOjB,SAASK,MAAM,GAAGf,UAAUyB,QAAQD,OAAO,CAAC;oBAAER,MAAM;oBAAMhB,OAAOA;gBAAiB;YAC3F;YAEA,IAAIoB,OAAOW,OAAO,EAAE;gBAClBJ;YACF,OAAO;gBACLP,OAAOY,gBAAgB,CAAC,SAASL;YACnC;YAEA,MAAMM,OAAO;gBAACV;gBAASW;aAAU;YAEjC,OAAO;gBACLrB,MAAK,GAAGC,IAAkB;oBACxBmB,IAAI,CAAC,EAAE,GAAGvB,SAASG,IAAI,IAAIC;oBAC3B,OAAOW,QAAQQ,IAAI,CAACA,MAAMhC,IAAI,CAAC,CAACK;wBAC9B,IAAIA,WAAW4B,WAAW;4BACxB,KAAKL;4BACL,OAAO;gCAAEb,MAAM;gCAAMhB,OAAOkC;4BAAqB;wBACnD;wBACA,IAAI5B,OAAOU,IAAI,EAAE;4BACfY,SAAS;4BACTR,OAAOU,mBAAmB,CAAC,SAASH;wBACtC;wBACA,OAAOrB;oBACT;gBACF;gBACAS,QAAOf,KAAe;oBACpB,OAAO6B,OAAO7B;gBAChB;YACF;QACF;IACF;AACF;AAuCA,OAAO,MAAMmC,UAAmB,CAACC,cAAuBC,kBAA2BC,OAAe,CAAC;IACjG,MAAMC,cAAcF,qBAAqBH;IACzC,MAAMM,QAAQD,cAAcH,eAAgB;IAC5C,MAAMK,QAAQL,iBAAiBF,YAAY3B,WAAWgC,cAAcF,mBAAmBD;IAEvF,OAAO;QACL,CAACf,OAAOX,QAAQ,CAAC;YACf,IAAIgC,MAAM;YACV,IAAIC,UAAUH;YACd,OAAO;gBACL3B;oBACE,IAAI6B,MAAMD,OAAO;wBACf,MAAMzC,QAAQ2C;wBACdA,WAAWL;wBACXI;wBACA,OAAO;4BAAE1C;4BAAOgB,MAAM;wBAAM;oBAC9B;oBACA,OAAOlB;gBACT;gBACAiB,QAAOf,KAAK;oBACV0C,MAAMD;oBACN,OAAO;wBAAEzC;wBAAOgB,MAAM;oBAAK;gBAC7B;gBACAC,OAAM2B,KAAe;oBACnBF,MAAMD;oBACN,MAAMG;gBACR;YACF;QACF;IACF;AACF,EAAE;AAmBF,OAAO,MAAMC,kBAAkB,OAAOC,SAAiB1B;IACrD,IAAIA,QAAQW,SAAS;QACnB,OAAO;IACT;IACA,MAAM,EAAER,OAAO,EAAEC,OAAO,EAAE,GAAGC,QAAQC,aAAa;IAClD,MAAMqB,UAAUC,WAAWxB,SAASsB,SAAS;IAC7C,MAAMnB,UAAU;QACdsB,aAAaF;QACbvB,QAAQ;IACV;IACAJ,QAAQY,iBAAiB,SAASL;IAElC,OAAOJ,QAAQ2B,OAAO,CAAC,IAAM9B,QAAQU,oBAAoB,SAASH;AACpE,EAAE;AAsBF,OAAO,MAAMwB,kBAAkB,CAAoBhC;IACjD,OAAO;QACL,CAACE,OAAOC,aAAa,CAAC;YACpB,MAAMZ,WAAWS,QAAQ,CAACE,OAAOX,QAAQ,CAAC;YAC1C,OAAO;gBACLG,MAAK,GAAGC,IAAkB;oBACxB,OAAOW,QAAQD,OAAO,CAACd,SAASG,IAAI,IAAIC;gBAC1C;gBACAC,QAAOqC,UAAU;oBACf,OAAO3B,QAAQD,OAAO,CAAC4B,YAAYnD,IAAI,CAAC,CAACD,QAAUU,SAASK,MAAM,GAAGf,UAAW;4BAAEA;4BAAOgB,MAAM;wBAAK;gBACtG;gBACAC,OAAM2B,KAAK;oBACT,IAAIlC,SAASO,KAAK,EAAE;wBAClB,OAAOQ,QAAQD,OAAO,CAACd,SAASO,KAAK,CAAC2B;oBACxC;oBACA,OAAOnB,QAAQ4B,MAAM,CAACT;gBACxB;YACF;QACF;IACF;AACF,EAAE;AA8BF,MAAMU,kBAAkB,CAAoBtD;IAC1C,OAAO,OAAO,AAACA,KAA0C,CAACqB,OAAOC,aAAa,CAAC,KAAK;AACtF;AAKA,OAAO,gBAAgBiC,KACrBpC,QAA0B,EAC1BqC,gBAAmE,EACnEpC,MAAoB;IAEpB,MAAMqC,SAASrC,SAASF,kBAAkBC,UAAUC,UAAUD;IAC9D,MAAMuC,YAAYF;IAElB,WAAW,MAAMxD,SAASyD,OAAQ;QAChC,MAAME,WAAWD,UAAU1D;QAC3B,MAAM4D,cAAcN,gBAAgBK,YAAYA,WAAWR,gBAAgBQ;QAC3E,MAAME,eAAezC,SAASF,kBAAkB0C,aAAaxC,UAAUwC;QAEvE,WAAW,MAAME,YAAYD,aAAc;YACzC,MAAMC;QACR;IACF;AACF;AAWA,OAAO,MAAMC,iBAAiB,CAAI,GAAGC;IACnC,OAAO;QACL,CAAC3C,OAAOC,aAAa,CAAC;YACpB,IAAI0C,UAAUC,MAAM,KAAK,GAAG;gBAC1B,OAAO;oBACLpD,MAAM,IAAMY,QAAQD,OAAO,CAAC1B;gBAC9B;YACF;YAEA,MAAMoE,OAAO7C,OAAO;YACpB,MAAM8C,OAAO,IAAIC;YACjB,MAAMC,WAAW,IAAIxE,SAAYsE,KAAK/C,MAAM;YAC5C,IAAIkD,YAAYN,UAAUC,MAAM;YAEhC,MAAMM,OAAO,OAAOpD;gBAClB,IAAI;oBACF,WAAW,MAAMnB,SAASkB,kBAAkBC,UAAUgD,KAAK/C,MAAM,EAAG;wBAClE,IAAI,CAACiD,SAASG,IAAI,CAACxE,QAAQ;4BACzB;wBACF;oBACF;gBACF,EAAE,OAAO4C,OAAO;oBACduB,KAAKM,KAAK,CAAC7B;gBACb,SAAU;oBACR0B,aAAa;oBACb,IAAIA,cAAc,KAAK,CAACH,KAAK/C,MAAM,CAACW,OAAO,EAAE;wBAC3CoC,KAAKM,KAAK,CAACP;oBACb;gBACF;YACF;YAEA,KAAK,MAAM/C,YAAY6C,UAAW;gBAChC,KAAKO,KAAKpD;YACZ;YAEA,OAAO;gBACLN,MAAM;oBACJ,IAAI;wBACF,MAAMb,QAAQ,MAAMqE,SAASK,OAAO;wBACpC,OAAO;4BAAE1E;4BAAOgB,MAAM;wBAAM;oBAC9B,EAAE,OAAM;wBACN,IAAImD,KAAK/C,MAAM,CAACW,OAAO,IAAIoC,KAAK/C,MAAM,CAACuD,MAAM,KAAKT,MAAM;4BACtD,OAAOpE;wBACT;wBACA,MAAMqE,KAAK/C,MAAM,CAACuD,MAAM;oBAC1B;gBACF;gBACA5D,QAAQ;oBACNoD,KAAKM,KAAK,CAACP;oBACX,OAAOpE;gBACT;gBACAmB,OAAO,OAAO2B;oBACZuB,KAAKM,KAAK,CAAC7B;oBACX,OAAO9C;gBACT;YACF;QACF;IACF;AACF,EAAE"}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "evnty",
|
|
3
3
|
"description": "Async-first, reactive event handling library for complex event flows in browser and Node.js",
|
|
4
|
-
"version": "5.
|
|
4
|
+
"version": "5.4.0",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"types": "build/index.d.ts",
|
|
7
7
|
"main": "build/index.cjs",
|
|
@@ -51,10 +51,10 @@
|
|
|
51
51
|
"devDependencies": {
|
|
52
52
|
"@eslint/js": "^10.0.1",
|
|
53
53
|
"@fast-check/vitest": "^0.4.0",
|
|
54
|
-
"@stryker-mutator/core": "^9.6.
|
|
55
|
-
"@stryker-mutator/typescript-checker": "^9.6.
|
|
56
|
-
"@stryker-mutator/vitest-runner": "^9.6.
|
|
57
|
-
"@types/node": "^25.
|
|
54
|
+
"@stryker-mutator/core": "^9.6.1",
|
|
55
|
+
"@stryker-mutator/typescript-checker": "^9.6.1",
|
|
56
|
+
"@stryker-mutator/vitest-runner": "^9.6.1",
|
|
57
|
+
"@types/node": "^25.6.0",
|
|
58
58
|
"@typescript-eslint/eslint-plugin": "^8.58.1",
|
|
59
59
|
"@typescript-eslint/parser": "^8.58.1",
|
|
60
60
|
"@typescript-eslint/typescript-estree": "^8.58.1",
|
|
@@ -64,10 +64,9 @@
|
|
|
64
64
|
"eslint": "^10.2.0",
|
|
65
65
|
"eslint-config-prettier": "^10.1.8",
|
|
66
66
|
"eslint-plugin-prettier": "^5.5.5",
|
|
67
|
-
"evnty-release": "npm:evnty@^5.3.2",
|
|
68
67
|
"inop": "^0.9.0",
|
|
69
68
|
"overtake": "2.1.1",
|
|
70
|
-
"prettier": "^3.8.
|
|
69
|
+
"prettier": "^3.8.2",
|
|
71
70
|
"recast": "^0.23.11",
|
|
72
71
|
"sass-embedded": "^1.99.0",
|
|
73
72
|
"typescript": "^6.0.2",
|
|
@@ -86,6 +85,8 @@
|
|
|
86
85
|
"docs:dev": "vuepress dev docs",
|
|
87
86
|
"docs:gen": "node ./scripts/docgen.ts src/*.ts",
|
|
88
87
|
"docs:update-package": "pnpm dlx vp-update",
|
|
89
|
-
"bench": "overtake src/__bench__/event.ts --progress"
|
|
88
|
+
"bench": "overtake src/__bench__/event.ts --pin-cores --progress -w 1",
|
|
89
|
+
"bench:test": "pnpm bench --compare-baseline .bench-baseline.json",
|
|
90
|
+
"bench:save": "pnpm bench --save-baseline .bench-baseline.json"
|
|
90
91
|
}
|
|
91
92
|
}
|
package/src/async.ts
CHANGED
|
@@ -38,6 +38,16 @@ export class Disposer {
|
|
|
38
38
|
}
|
|
39
39
|
}
|
|
40
40
|
|
|
41
|
+
/**
|
|
42
|
+
* @internal
|
|
43
|
+
*/
|
|
44
|
+
export const ITERATOR_DONE: IteratorResult<never, void> = Object.freeze({ value: undefined, done: true });
|
|
45
|
+
|
|
46
|
+
/**
|
|
47
|
+
* @internal
|
|
48
|
+
*/
|
|
49
|
+
export const ITERATOR_DONE_PROMISE: Promise<IteratorResult<never, void>> = Promise.resolve(ITERATOR_DONE);
|
|
50
|
+
|
|
41
51
|
/**
|
|
42
52
|
* @internal
|
|
43
53
|
*/
|
|
@@ -84,19 +94,17 @@ export abstract class Async<T, R> implements Emitter<T, R>, Promiseable<T>, Prom
|
|
|
84
94
|
return this.receive().then(onfulfilled, onrejected);
|
|
85
95
|
}
|
|
86
96
|
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
return { value: undefined, done: true };
|
|
93
|
-
}
|
|
97
|
+
next(): Promise<IteratorResult<T, void>> {
|
|
98
|
+
return this.receive().then(
|
|
99
|
+
(value) => ({ value, done: false }),
|
|
100
|
+
() => ITERATOR_DONE,
|
|
101
|
+
);
|
|
94
102
|
}
|
|
95
103
|
|
|
96
|
-
|
|
104
|
+
return(): Promise<IteratorResult<T, void>> {
|
|
97
105
|
// Stryker disable next-line OptionalChaining: all subclasses define dispose()
|
|
98
106
|
this.dispose?.();
|
|
99
|
-
return
|
|
107
|
+
return ITERATOR_DONE_PROMISE;
|
|
100
108
|
}
|
|
101
109
|
|
|
102
110
|
[Symbol.asyncIterator](): AsyncIterator<T, void, void> {
|
package/src/broadcast.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { RingBuffer } from './ring-buffer.js';
|
|
2
2
|
import { Signal } from './signal.js';
|
|
3
|
-
import { Disposer } from './async.js';
|
|
3
|
+
import { Disposer, ITERATOR_DONE, ITERATOR_DONE_PROMISE } from './async.js';
|
|
4
4
|
import { min } from './utils.js';
|
|
5
5
|
import { Action, Fn, Emitter, MaybePromise, Promiseable } from './types.js';
|
|
6
6
|
|
|
@@ -63,13 +63,13 @@ export class BroadcastIterator<T> implements AsyncIterator<T, void, void> {
|
|
|
63
63
|
await this.#signal.receive();
|
|
64
64
|
}
|
|
65
65
|
} catch {
|
|
66
|
-
return
|
|
66
|
+
return ITERATOR_DONE;
|
|
67
67
|
}
|
|
68
68
|
}
|
|
69
69
|
|
|
70
|
-
|
|
70
|
+
return(): Promise<IteratorResult<T, void>> {
|
|
71
71
|
this.#broadcast.leave(this.#handle);
|
|
72
|
-
return
|
|
72
|
+
return ITERATOR_DONE_PROMISE;
|
|
73
73
|
}
|
|
74
74
|
}
|
|
75
75
|
|
|
@@ -302,7 +302,7 @@ export class Broadcast<T> implements Emitter<T, boolean>, Promiseable<T>, Promis
|
|
|
302
302
|
const cursor = this.#cursors.get(id);
|
|
303
303
|
if (cursor === undefined) throw new Error('Invalid handle');
|
|
304
304
|
if (cursor >= this.#buffer.right) {
|
|
305
|
-
return
|
|
305
|
+
return ITERATOR_DONE;
|
|
306
306
|
}
|
|
307
307
|
|
|
308
308
|
const value = this.#buffer.peekAt(cursor)!;
|
package/src/event.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Callback, Listener, FilterFunction, Predicate, Mapper, Reducer, Action, Fn, Emitter, MaybePromise, Promiseable } from './types.js';
|
|
2
|
-
import { Disposer } from './async.js';
|
|
2
|
+
import { Disposer, ITERATOR_DONE, ITERATOR_DONE_PROMISE } from './async.js';
|
|
3
3
|
import { Signal } from './signal.js';
|
|
4
4
|
import { ListenerRegistry } from './listener-registry.js';
|
|
5
5
|
import { DispatchResult } from './dispatch-result.js';
|
|
@@ -16,17 +16,15 @@ export class EventIterator<T> implements AsyncIterator<T, void, void> {
|
|
|
16
16
|
this.#signal = signal;
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
return { value: undefined, done: true };
|
|
25
|
-
}
|
|
19
|
+
next(): Promise<IteratorResult<T, void>> {
|
|
20
|
+
return this.#signal.receive().then(
|
|
21
|
+
(value): IteratorResult<T, void> => ({ value, done: false }),
|
|
22
|
+
(): IteratorResult<T, void> => ITERATOR_DONE,
|
|
23
|
+
);
|
|
26
24
|
}
|
|
27
25
|
|
|
28
|
-
|
|
29
|
-
return
|
|
26
|
+
return(): Promise<IteratorResult<T, void>> {
|
|
27
|
+
return ITERATOR_DONE_PROMISE;
|
|
30
28
|
}
|
|
31
29
|
}
|
|
32
30
|
|
package/src/iterator.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { mergeIterables, toAsyncIterable, pipe, isThenable } from './utils.js';
|
|
2
|
+
import { ITERATOR_DONE } from './async.js';
|
|
2
3
|
import { AnyIterable } from './types.js';
|
|
3
4
|
|
|
4
5
|
const enum OpKind {
|
|
@@ -344,30 +345,30 @@ function createSimpleIterable(source: AsyncIterable<unknown, unknown, unknown>,
|
|
|
344
345
|
if (checkTakeExhausted(takeStates)) {
|
|
345
346
|
done = true;
|
|
346
347
|
await iterator.return?.();
|
|
347
|
-
return
|
|
348
|
+
return ITERATOR_DONE;
|
|
348
349
|
}
|
|
349
350
|
|
|
350
351
|
const sourceResult = await iterator.next();
|
|
351
352
|
if (sourceResult.done) {
|
|
352
353
|
done = true;
|
|
353
|
-
return
|
|
354
|
+
return ITERATOR_DONE;
|
|
354
355
|
}
|
|
355
356
|
|
|
356
357
|
const result = await processOpsSimple(sourceResult.value, ops, opStates);
|
|
357
358
|
if (result.done) {
|
|
358
359
|
done = true;
|
|
359
360
|
await iterator.return?.();
|
|
360
|
-
return
|
|
361
|
+
return ITERATOR_DONE;
|
|
361
362
|
}
|
|
362
363
|
if (result.shouldYield) return { value: result.value, done: false };
|
|
363
364
|
}
|
|
364
|
-
return
|
|
365
|
+
return ITERATOR_DONE;
|
|
365
366
|
},
|
|
366
367
|
|
|
367
368
|
async return(returnValue?: unknown): Promise<IteratorResult<unknown, void>> {
|
|
368
369
|
done = true;
|
|
369
370
|
await iterator.return?.(returnValue);
|
|
370
|
-
return
|
|
371
|
+
return ITERATOR_DONE;
|
|
371
372
|
},
|
|
372
373
|
|
|
373
374
|
async throw(error?: unknown): Promise<IteratorResult<unknown, void>> {
|
|
@@ -408,7 +409,7 @@ function createExpandingIterable(source: AsyncIterable<unknown, unknown, unknown
|
|
|
408
409
|
done = true;
|
|
409
410
|
await closeInnerIterators();
|
|
410
411
|
await iterator.return?.();
|
|
411
|
-
return
|
|
412
|
+
return ITERATOR_DONE;
|
|
412
413
|
}
|
|
413
414
|
if (result.expandIterator) {
|
|
414
415
|
innerStack.push({ type: 'expand', iterator: result.expandIterator, opIndex: result.expandOpIndex });
|
|
@@ -455,13 +456,13 @@ function createExpandingIterable(source: AsyncIterable<unknown, unknown, unknown
|
|
|
455
456
|
if (checkTakeExhausted(takeStates)) {
|
|
456
457
|
done = true;
|
|
457
458
|
await iterator.return?.();
|
|
458
|
-
return
|
|
459
|
+
return ITERATOR_DONE;
|
|
459
460
|
}
|
|
460
461
|
|
|
461
462
|
const sourceResult = await iterator.next();
|
|
462
463
|
if (sourceResult.done) {
|
|
463
464
|
done = true;
|
|
464
|
-
return
|
|
465
|
+
return ITERATOR_DONE;
|
|
465
466
|
}
|
|
466
467
|
|
|
467
468
|
const result = await processOps(sourceResult.value, ops, opStates, 0);
|
|
@@ -469,14 +470,14 @@ function createExpandingIterable(source: AsyncIterable<unknown, unknown, unknown
|
|
|
469
470
|
if (handled) return handled;
|
|
470
471
|
}
|
|
471
472
|
|
|
472
|
-
return
|
|
473
|
+
return ITERATOR_DONE;
|
|
473
474
|
},
|
|
474
475
|
|
|
475
476
|
async return(returnValue?: unknown): Promise<IteratorResult<unknown, void>> {
|
|
476
477
|
done = true;
|
|
477
478
|
await closeInnerIterators();
|
|
478
479
|
await iterator.return?.(returnValue);
|
|
479
|
-
return
|
|
480
|
+
return ITERATOR_DONE;
|
|
480
481
|
},
|
|
481
482
|
|
|
482
483
|
async throw(error?: unknown): Promise<IteratorResult<unknown, void>> {
|
package/src/sequence.ts
CHANGED
|
@@ -122,10 +122,9 @@ export class Sequence<T> extends Async<T, boolean> {
|
|
|
122
122
|
* sequence.emit('new item'); // Safe to add, queue has space
|
|
123
123
|
* ```
|
|
124
124
|
*/
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
}
|
|
125
|
+
reserve(capacity: number): Promise<void> {
|
|
126
|
+
if (this.#queue.length <= capacity) return Promise.resolve();
|
|
127
|
+
return this.#sendSignal.receive().then(() => this.reserve(capacity));
|
|
129
128
|
}
|
|
130
129
|
|
|
131
130
|
/**
|
|
@@ -165,12 +164,12 @@ export class Sequence<T> extends Async<T, boolean> {
|
|
|
165
164
|
* const value = await valuePromise; // 42
|
|
166
165
|
* ```
|
|
167
166
|
*/
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
167
|
+
receive(): Promise<T> {
|
|
168
|
+
if (this.#queue.length) {
|
|
169
|
+
this.#sendSignal.emit();
|
|
170
|
+
return Promise.resolve(this.#queue.shift()!);
|
|
171
171
|
}
|
|
172
|
-
this.#
|
|
173
|
-
return this.#queue.shift()!;
|
|
172
|
+
return this.#nextSignal.receive().then(() => this.receive());
|
|
174
173
|
}
|
|
175
174
|
|
|
176
175
|
/**
|