From e13a6d3e4f807482f77b5a9c8e4610080b369a77 Mon Sep 17 00:00:00 2001 From: Matthew Podwysocki Date: Mon, 25 Jul 2022 20:11:00 -0400 Subject: [PATCH] chore(types): Fixing types (#341) * chore(types): Fixing types * fix(from/as): Remove from/as as separate factories * fix(from/as): remove iterable from/as * test: fix minification issues affecting tests * chore(sourcemaps): fix sourcemap errors during build * style: asIterable() and asAsyncIterable() -> as() * build(tests): update jest and ts-jest versions Co-authored-by: Matthew Podwysocki Co-authored-by: ptaylor --- .github/workflows/main.pr.yml | 2 + gulp/closure-task.js | 2 + package.json | 6 +- spec/asynciterable-operators/groupby-spec.ts | 8 +- spec/asynciterable-operators/repeat-spec.ts | 6 +- spec/asynciterable-operators/slice-spec.ts | 12 +- .../asynciterable-operators/takeuntil-spec.ts | 3 +- .../todomstream-spec.ts | 18 +- spec/asynciterable/as-spec.ts | 18 +- spec/asynciterable/asasynciterable-spec.ts | 6 +- spec/asynciterable/fromdomstream-spec.ts | 6 +- spec/asynciterable/fromevent-spec.ts | 16 +- spec/asynciterable/fromeventpattern-spec.ts | 18 + spec/asynciterable/fromnodestream-spec.ts | 6 +- spec/asynciterable/toarray-spec.ts | 4 +- spec/asynciterable/tonodestream-spec.ts | 14 +- spec/asynciterable/toobservable-spec.ts | 20 +- spec/asynciterable/toset-spec.ts | 6 +- spec/asynciterablehelpers.ts | 4 +- spec/iterable-operators/groupby-spec.ts | 8 +- spec/iterable-operators/groupjoin-spec.ts | 16 +- spec/iterable-operators/innerjoin-spec.ts | 20 +- spec/iterable-operators/intersect-spec.ts | 6 +- spec/iterable-operators/map-spec.ts | 12 +- spec/iterable-operators/orderby-spec.ts | 12 +- spec/iterable-operators/pairwise-spec.ts | 8 +- spec/iterable-operators/pluck-spec.ts | 8 +- spec/iterable-operators/repeat-spec.ts | 10 +- spec/iterable-operators/skip-spec.ts | 10 +- spec/iterable-operators/skipwhile-spec.ts | 14 +- spec/iterable-operators/slice-spec.ts | 22 +- spec/iterable-operators/takewhile-spec.ts | 4 +- spec/iterable/as-spec.ts | 10 +- spec/iterable/todomstream-spec.ts | 18 +- spec/iterable/tonodestream-spec.ts | 16 +- spec/tsconfig/tsconfig.es2015.umd.json | 3 +- spec/tsconfig/tsconfig.es5.umd.json | 3 +- spec/tsconfig/tsconfig.esnext.umd.json | 3 +- src/Ix.node.ts | 4 - src/Ix.ts | 3 +- src/add/asynciterable-operators/switchmap.ts | 2 +- src/add/asynciterable/as.ts | 12 - src/add/asynciterable/from.ts | 16 - src/add/iterable/as.ts | 12 - src/add/iterable/from.ts | 16 - src/asynciterable/as.ts | 67 ---- src/asynciterable/asynciterablex.ts | 331 ++++++++++++++++-- src/asynciterable/from.ts | 192 ---------- src/asynciterable/fromevent.ts | 68 +++- src/asynciterable/fromeventpattern.ts | 36 +- src/asynciterable/index.ts | 8 +- src/asynciterable/operators/_flatten.ts | 3 +- src/asynciterable/operators/groupjoin.ts | 3 +- src/asynciterable/operators/mergeall.ts | 4 +- src/asynciterable/operators/startwith.ts | 13 +- src/asynciterable/operators/switchmap.ts | 2 +- src/asynciterable/pipe.ts | 95 ----- src/asynciterable/toobservable.ts | 3 + src/iterable/as.ts | 52 --- src/iterable/from.ts | 70 ---- src/iterable/index.ts | 7 +- src/iterable/iterablex.ts | 116 +++++- src/iterable/pipe.ts | 92 ----- src/iterable/todomstream.ts | 6 +- 64 files changed, 732 insertions(+), 879 deletions(-) delete mode 100644 src/add/asynciterable/as.ts delete mode 100644 src/add/asynciterable/from.ts delete mode 100644 src/add/iterable/as.ts delete mode 100644 src/add/iterable/from.ts delete mode 100644 src/asynciterable/as.ts delete mode 100644 src/asynciterable/from.ts delete mode 100644 src/asynciterable/pipe.ts delete mode 100644 src/iterable/as.ts delete mode 100644 src/iterable/from.ts delete mode 100644 src/iterable/pipe.ts diff --git a/.github/workflows/main.pr.yml b/.github/workflows/main.pr.yml index 602691cb..edd9f08d 100644 --- a/.github/workflows/main.pr.yml +++ b/.github/workflows/main.pr.yml @@ -58,6 +58,8 @@ jobs: node: [14.x, 16.x, 18.x] module: [cjs, esm, umd] target: [es5, es2015, esnext] + exclude: + - {node: 14.x, target: esnext} steps: - name: Setup node v${{ matrix.node }} uses: actions/setup-node@v3 diff --git a/gulp/closure-task.js b/gulp/closure-task.js index f6d0be4a..b93b30e4 100644 --- a/gulp/closure-task.js +++ b/gulp/closure-task.js @@ -162,6 +162,8 @@ Symbol.iterator; Symbol.observable; /** @type {symbol} */ Symbol.asyncIterator; +/** @type {symbol} */ +var symbolObservable = function() {}; `); } diff --git a/package.json b/package.json index bcae4839..9630c3cb 100644 --- a/package.json +++ b/package.json @@ -70,14 +70,14 @@ "eslint-plugin-jest": "26.1.1", "esm": "https://github.com/jsg2021/esm/releases/download/v3.x.x-pr883/esm-3.x.x-pr883.tgz", "glob": "7.1.6", - "google-closure-compiler": "20220202.0.0", + "google-closure-compiler": "20220601.0.0", "gulp": "4.0.2", "gulp-json-transform": "0.4.7", "gulp-rename": "2.0.0", "gulp-sourcemaps": "2.6.5", "gulp-typescript": "5.0.1", "husky": "4.2.3", - "jest": "27.5.1", + "jest": "28.1.3", "jest-environment-node-debug": "2.0.0", "jest-silent-reporter": "0.5.0", "json": "9.0.6", @@ -95,7 +95,7 @@ "source-map-loader": "0.2.4", "terser": "4.6.4", "terser-webpack-plugin": "2.3.5", - "ts-jest": "27.1.3", + "ts-jest": "28.0.7", "ts-node": "8.6.2", "typedoc": "0.16.10", "typescript": "4.6.2", diff --git a/spec/asynciterable-operators/groupby-spec.ts b/spec/asynciterable-operators/groupby-spec.ts index 14ba0e5d..dc06b57f 100644 --- a/spec/asynciterable-operators/groupby-spec.ts +++ b/spec/asynciterable-operators/groupby-spec.ts @@ -1,5 +1,5 @@ import { hasNext, noNext } from '../asynciterablehelpers'; -import { empty, from } from 'ix/asynciterable'; +import { empty, AsyncIterableX } from 'ix/asynciterable'; import { groupBy } from 'ix/asynciterable/operators'; interface Employee { @@ -17,7 +17,7 @@ test('AsyncIterable#groupBy normal', async () => { { name: 'Lisa', age: 23 }, { name: 'Eric', age: 42 }, ]; - const xss = from(xs); + const xss = AsyncIterableX.from(xs); const ys = xss.pipe(groupBy(async (x) => Math.floor(x.age / 10))); const it = ys[Symbol.asyncIterator](); @@ -65,7 +65,7 @@ test('AsyncIterable#groupBy normal can get results later', async () => { { name: 'Lisa', age: 23 }, { name: 'Eric', age: 42 }, ]; - const xss = from(xs); + const xss = AsyncIterableX.from(xs); const ys = xss.pipe(groupBy(async (x) => Math.floor(x.age / 10))); const it = ys[Symbol.asyncIterator](); @@ -117,7 +117,7 @@ test('AsyncIterable#groupBy empty', async () => { test('AsyncIterable#groupBy element selector', async () => { const xs = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]; - const xss = from(xs); + const xss = AsyncIterableX.from(xs); const ys = xss.pipe( groupBy( async (x) => x % 3, diff --git a/spec/asynciterable-operators/repeat-spec.ts b/spec/asynciterable-operators/repeat-spec.ts index 4ce3b9a0..db0ad1c9 100644 --- a/spec/asynciterable-operators/repeat-spec.ts +++ b/spec/asynciterable-operators/repeat-spec.ts @@ -1,6 +1,6 @@ import '../asynciterablehelpers'; import { sum } from 'ix/iterable'; -import { from, every, of, toArray } from 'ix/asynciterable'; +import { as, every, of, toArray } from 'ix/asynciterable'; import { buffer, map, repeat, tap, take } from 'ix/asynciterable/operators'; test('AsyncIterable#repeat infinite', async () => { @@ -18,7 +18,7 @@ test('AsyncIterable#repeat infinite', async () => { expect(10).toBe(res.length); expect( every( - from(res).pipe( + as(res).pipe( buffer(2), map((b) => sum(b)) ), @@ -40,7 +40,7 @@ test('AsyncIterable#repeat finite', async () => { expect(10).toBe(res.length); expect( every( - from(res).pipe( + as(res).pipe( buffer(2), map((b) => sum(b)) ), diff --git a/spec/asynciterable-operators/slice-spec.ts b/spec/asynciterable-operators/slice-spec.ts index f445448e..e39b0cd0 100644 --- a/spec/asynciterable-operators/slice-spec.ts +++ b/spec/asynciterable-operators/slice-spec.ts @@ -1,9 +1,9 @@ import { hasNext, noNext } from '../asynciterablehelpers'; import { slice } from 'ix/asynciterable/operators'; -import { from } from 'ix/asynciterable'; +import { as } from 'ix/asynciterable'; test('AsyncIterable#slice slices at zero with one item', async () => { - const xs = from([1, 2, 3, 4]); + const xs = as([1, 2, 3, 4]); const ys = xs.pipe(slice(0, 1)); const it = ys[Symbol.asyncIterator](); @@ -12,7 +12,7 @@ test('AsyncIterable#slice slices at zero with one item', async () => { }); test('AsyncIterable#slice slices at one with one item', async () => { - const xs = from([1, 2, 3, 4]); + const xs = as([1, 2, 3, 4]); const ys = xs.pipe(slice(1, 1)); const it = ys[Symbol.asyncIterator](); @@ -21,7 +21,7 @@ test('AsyncIterable#slice slices at one with one item', async () => { }); test('AsyncIterable#slice slices at one with multiple items', async () => { - const xs = from([1, 2, 3, 4]); + const xs = as([1, 2, 3, 4]); const ys = xs.pipe(slice(1, 2)); const it = ys[Symbol.asyncIterator](); @@ -31,7 +31,7 @@ test('AsyncIterable#slice slices at one with multiple items', async () => { }); test('AsyncIterable#slice slices at one with no end', async () => { - const xs = from([1, 2, 3, 4]); + const xs = as([1, 2, 3, 4]); const ys = xs.pipe(slice(1)); const it = ys[Symbol.asyncIterator](); @@ -42,7 +42,7 @@ test('AsyncIterable#slice slices at one with no end', async () => { }); test('AsyncIterable#slice slices at zero with no end', async () => { - const xs = from([1, 2, 3, 4]); + const xs = as([1, 2, 3, 4]); const ys = xs.pipe(slice(0)); const it = ys[Symbol.asyncIterator](); diff --git a/spec/asynciterable-operators/takeuntil-spec.ts b/spec/asynciterable-operators/takeuntil-spec.ts index 93b0aca5..ddab6bb3 100644 --- a/spec/asynciterable-operators/takeuntil-spec.ts +++ b/spec/asynciterable-operators/takeuntil-spec.ts @@ -1,7 +1,6 @@ import { hasNext, noNext, delayValue } from '../asynciterablehelpers'; import { takeUntil } from 'ix/asynciterable/operators'; -import { as } from 'ix/asynciterable'; -import { AsyncSink } from 'ix/asynciterable'; +import { as, AsyncSink } from 'ix/asynciterable'; test('AsyncIterable#takeUntil hits', async () => { const xs = async function* () { diff --git a/spec/asynciterable-operators/todomstream-spec.ts b/spec/asynciterable-operators/todomstream-spec.ts index fc7c0e0f..0ce1e097 100644 --- a/spec/asynciterable-operators/todomstream-spec.ts +++ b/spec/asynciterable-operators/todomstream-spec.ts @@ -1,5 +1,5 @@ import '../asynciterablehelpers'; -import { from } from 'ix/asynciterable'; +import { as } from 'ix/asynciterable'; import { map, toDOMStream } from 'ix/asynciterable/operators'; // eslint-disable-next-line consistent-return @@ -10,7 +10,7 @@ import { map, toDOMStream } from 'ix/asynciterable/operators'; }); } - const stringsItr = () => from([1, 2, 3]).pipe(map((i) => `${i}`)); + const stringsItr = () => as([1, 2, 3]).pipe(map((i) => `${i}`)); const buffersItr = () => stringsItr().pipe(map((val) => Buffer.from(val))); const objectsItr = () => stringsItr().pipe(map((val) => ({ val }))); const compare = (a: T, b: T) => { @@ -31,17 +31,17 @@ import { map, toDOMStream } from 'ix/asynciterable/operators'; const expectedObjects = expectedStrings.map((val) => ({ val })); const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { - const expected = from(expectedStrings); + const expected = as(expectedStrings); const actual = stringsItr().pipe(toDOMStream()); await expect(actual).toEqualStream(expected, compare); }); test('yields Buffers', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = buffersItr().pipe(toDOMStream()); await expect(actual).toEqualStream(expected, compare); }); test('yields Objects', async () => { - const expected = from(expectedObjects); + const expected = as(expectedObjects); const actual = objectsItr().pipe(toDOMStream()); await expect(actual).toEqualStream(expected, compare); }); @@ -51,14 +51,14 @@ import { map, toDOMStream } from 'ix/asynciterable/operators'; const expectedStrings = ['123']; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = stringsItr() .pipe(map((x) => Buffer.from(x))) .pipe(toDOMStream({ type: 'bytes' })); await expect(actual).toEqualStream(expected, compare); }); test('yields Buffers', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = buffersItr().pipe(toDOMStream({ type: 'bytes' })); await expect(actual).toEqualStream(expected, compare); }); @@ -68,14 +68,14 @@ import { map, toDOMStream } from 'ix/asynciterable/operators'; const expectedStrings = ['123']; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = stringsItr() .pipe(map((x) => Buffer.from(x))) .pipe(toDOMStream({ type: 'bytes', autoAllocateChunkSize: 1024 })); await expect(actual).toEqualStream(expected, compare); }); test('yields Buffers', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = buffersItr().pipe( toDOMStream({ type: 'bytes', autoAllocateChunkSize: 1024 }) ); diff --git a/spec/asynciterable/as-spec.ts b/spec/asynciterable/as-spec.ts index 9c982043..8f3b4a4d 100644 --- a/spec/asynciterable/as-spec.ts +++ b/spec/asynciterable/as-spec.ts @@ -1,9 +1,9 @@ import { hasNext, noNext } from '../asynciterablehelpers'; -import { as } from 'ix/asynciterable'; +import { AsyncIterableX } from 'ix/asynciterable'; test('AsyncIterable#as from non-iterable', async () => { const xs = {}; - const res = as(xs); + const res = AsyncIterableX.as(xs); const it = res[Symbol.asyncIterator](); await hasNext(it, xs); @@ -12,7 +12,7 @@ test('AsyncIterable#as from non-iterable', async () => { test('AsyncIterable#as from string emits the string, not chars', async () => { const x = 'foo'; - const res = as(x); + const res = AsyncIterableX.as(x); const it = res[Symbol.asyncIterator](); await hasNext(it, x); await noNext(it); @@ -24,7 +24,7 @@ test('AsyncIterable#as from promise list', async () => { Promise.resolve(2), Promise.resolve(3), ]; - const res = as(xs); + const res = AsyncIterableX.as(xs); const it = res[Symbol.asyncIterator](); await hasNext(it, 1); @@ -41,7 +41,7 @@ async function* getData(): AsyncIterable { test('AsyncIterable#as from async generator', async () => { const xs = getData(); - const res = as(xs); + const res = AsyncIterableX.as(xs); const it = res[Symbol.asyncIterator](); await hasNext(it, 1); @@ -52,7 +52,7 @@ test('AsyncIterable#as from async generator', async () => { test('AsyncIterable#as from array/iterable', async () => { const xs = [1, 2, 3]; - const res = as(xs); + const res = AsyncIterableX.as(xs); const it = res[Symbol.asyncIterator](); await hasNext(it, 1); @@ -63,7 +63,7 @@ test('AsyncIterable#as from array/iterable', async () => { test('AsyncIterable#as from empty array/iterable', async () => { const xs: number[] = []; - const res = as(xs); + const res = AsyncIterableX.as(xs); const it = res[Symbol.asyncIterator](); await noNext(it); @@ -71,7 +71,7 @@ test('AsyncIterable#as from empty array/iterable', async () => { test('AsyncIterable#as from array-like', async () => { const xs = { length: 3 }; - const res = as(xs); + const res = AsyncIterableX.as(xs); const it = res[Symbol.asyncIterator](); await hasNext(it, undefined); @@ -82,7 +82,7 @@ test('AsyncIterable#as from array-like', async () => { test('AsyncIterable#as from promise', async () => { const xs = Promise.resolve(42); - const res = as(xs); + const res = AsyncIterableX.as(xs); const it = res[Symbol.asyncIterator](); await hasNext(it, 42); diff --git a/spec/asynciterable/asasynciterable-spec.ts b/spec/asynciterable/asasynciterable-spec.ts index b0b7614d..6ec43173 100644 --- a/spec/asynciterable/asasynciterable-spec.ts +++ b/spec/asynciterable/asasynciterable-spec.ts @@ -1,5 +1,5 @@ import '../asynciterablehelpers'; -import { from } from 'ix/asynciterable'; +import { as } from 'ix/asynciterable'; import { Readable, ReadableOptions } from 'stream'; import { asAsyncIterable } from 'ix/asynciterable/asasynciterable'; @@ -34,7 +34,7 @@ import { asAsyncIterable } from 'ix/asynciterable/asasynciterable'; const xs = c.pipe( asAsyncIterable({ objectMode: true }) ); - const expected = from(['1', '2', '3']); + const expected = as(['1', '2', '3']); await expect(xs).toEqualStream(expected, compare); }); @@ -43,7 +43,7 @@ import { asAsyncIterable } from 'ix/asynciterable/asasynciterable'; const xs = c.pipe( asAsyncIterable({ objectMode: false }) ); - const expected = from(['123']); + const expected = as(['123']); await expect(xs).toEqualStream(expected, compare); }); }); diff --git a/spec/asynciterable/fromdomstream-spec.ts b/spec/asynciterable/fromdomstream-spec.ts index dd2e1dc2..1dd4a964 100644 --- a/spec/asynciterable/fromdomstream-spec.ts +++ b/spec/asynciterable/fromdomstream-spec.ts @@ -1,6 +1,6 @@ import '../asynciterablehelpers'; import { Readable, ReadableOptions } from 'stream'; -import { from, fromDOMStream } from 'ix/asynciterable'; +import { as, fromDOMStream } from 'ix/asynciterable'; // eslint-disable-next-line consistent-return (() => { @@ -44,14 +44,14 @@ import { from, fromDOMStream } from 'ix/asynciterable'; test('objectMode: true', async () => { const c = toStream(new Counter({ objectMode: true })); const xs = fromDOMStream(c) as AsyncIterable; - const expected = from(['1', '2', '3']); + const expected = as(['1', '2', '3']); await expect(xs).toEqualStream(expected, compare); }); test('objectMode: false', async () => { const c = toStream(new Counter({ objectMode: false })); const xs = fromDOMStream(c) as AsyncIterable; - const expected = from(['1', '2', '3'].map((s) => Buffer.from(s))); + const expected = as(['1', '2', '3'].map((s) => Buffer.from(s))); await expect(xs).toEqualStream(expected, compare); }); }); diff --git a/spec/asynciterable/fromevent-spec.ts b/spec/asynciterable/fromevent-spec.ts index 5d771123..885e3f60 100644 --- a/spec/asynciterable/fromevent-spec.ts +++ b/spec/asynciterable/fromevent-spec.ts @@ -6,7 +6,7 @@ const EVENT_TYPE = 'data'; test('AsyncIterable#fromEvent writes before emit', async () => { const e = new EventEmitter(); - const a = fromEvent(e, EVENT_TYPE); + const a = fromEvent(e, EVENT_TYPE); e.emit(EVENT_TYPE, 1); e.emit(EVENT_TYPE, 2); @@ -17,3 +17,17 @@ test('AsyncIterable#fromEvent writes before emit', async () => { await hasNext(it, 2); await hasNext(it, 3); }); + +test('AsyncIterable#fromEvent has selector', async () => { + const e = new EventEmitter(); + const a = fromEvent(e, EVENT_TYPE, (x) => x * 2); + + e.emit(EVENT_TYPE, 1); + e.emit(EVENT_TYPE, 2); + e.emit(EVENT_TYPE, 3); + + const it = a[Symbol.asyncIterator](); + await hasNext(it, 2); + await hasNext(it, 4); + await hasNext(it, 6); +}); diff --git a/spec/asynciterable/fromeventpattern-spec.ts b/spec/asynciterable/fromeventpattern-spec.ts index 1cfefdc1..f12de28f 100644 --- a/spec/asynciterable/fromeventpattern-spec.ts +++ b/spec/asynciterable/fromeventpattern-spec.ts @@ -20,3 +20,21 @@ test('AsyncIterable#fromEventPattern writes before emit', async () => { await hasNext(it, 2); await hasNext(it, 3); }); + +test('AsyncIterable#fromEventPattern has selector', async () => { + const e = new EventEmitter(); + const a = fromEventPattern( + (h) => e.addListener(EVENT_TYPE, h), + (h) => e.removeListener(EVENT_TYPE, h), + (x) => x * 2 + ); + + e.emit(EVENT_TYPE, 1); + e.emit(EVENT_TYPE, 2); + e.emit(EVENT_TYPE, 3); + + const it = a[Symbol.asyncIterator](); + await hasNext(it, 2); + await hasNext(it, 4); + await hasNext(it, 6); +}); diff --git a/spec/asynciterable/fromnodestream-spec.ts b/spec/asynciterable/fromnodestream-spec.ts index d9d91439..f3132558 100644 --- a/spec/asynciterable/fromnodestream-spec.ts +++ b/spec/asynciterable/fromnodestream-spec.ts @@ -1,5 +1,5 @@ import '../asynciterablehelpers'; -import { from } from 'ix/asynciterable'; +import { as } from 'ix/asynciterable'; import { Readable, ReadableOptions } from 'stream'; import { fromNodeStream } from 'ix/asynciterable/fromnodestream'; @@ -32,14 +32,14 @@ import { fromNodeStream } from 'ix/asynciterable/fromnodestream'; test('objectMode: true', async () => { const c = new Counter({ objectMode: true }); const xs = fromNodeStream(c) as AsyncIterable; - const expected = from(['1', '2', '3']); + const expected = as(['1', '2', '3']); await expect(xs).toEqualStream(expected, compare); }); test('objectMode: false', async () => { const c = new Counter({ objectMode: false }); const xs = fromNodeStream(c) as AsyncIterable; - const expected = from(['123']); + const expected = as(['123']); await expect(xs).toEqualStream(expected, compare); }); }); diff --git a/spec/asynciterable/toarray-spec.ts b/spec/asynciterable/toarray-spec.ts index d517280c..964c2d62 100644 --- a/spec/asynciterable/toarray-spec.ts +++ b/spec/asynciterable/toarray-spec.ts @@ -1,10 +1,10 @@ import '../asynciterablehelpers'; -import { empty, from, toArray } from 'ix/asynciterable'; +import { empty, as, toArray } from 'ix/asynciterable'; import { sequenceEqual } from 'ix/iterable'; test('AsyncIterable#toArray some', async () => { const xs = [42, 25, 39]; - const ys = from(xs); + const ys = as(xs); const res = await toArray(ys); expect(sequenceEqual(res, xs)).toBeTruthy(); }); diff --git a/spec/asynciterable/tonodestream-spec.ts b/spec/asynciterable/tonodestream-spec.ts index 0be76dd5..c5220176 100644 --- a/spec/asynciterable/tonodestream-spec.ts +++ b/spec/asynciterable/tonodestream-spec.ts @@ -1,5 +1,5 @@ import '../asynciterablehelpers'; -import { from } from 'ix/asynciterable'; +import { as } from 'ix/asynciterable'; import { AsyncIterableReadable } from 'ix/Ix.node'; import { map, toNodeStream } from 'ix/asynciterable/operators/index.node'; @@ -11,7 +11,7 @@ import { map, toNodeStream } from 'ix/asynciterable/operators/index.node'; }); } - const stringsItr = () => from([1, 2, 3]).pipe(map((i) => `${i}`)); + const stringsItr = () => as([1, 2, 3]).pipe(map((i) => `${i}`)); const buffersItr = () => stringsItr().pipe(map((val) => Buffer.from(val))); const objectsItr = () => stringsItr().pipe(map((val) => ({ val }))); const compare = (a: T, b: T) => { @@ -33,19 +33,19 @@ import { map, toNodeStream } from 'ix/asynciterable/operators/index.node'; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { await expect(stringsItr().pipe(toNodeStream({ objectMode: true }))).toEqualStream( - from(expectedStrings), + as(expectedStrings), compare ); }); test('yields Buffers', async () => { await expect(buffersItr().pipe(toNodeStream({ objectMode: true }))).toEqualStream( - from(expectedBuffers), + as(expectedBuffers), compare ); }); test('yields Objects', async () => { await expect(objectsItr().pipe(toNodeStream({ objectMode: true }))).toEqualStream( - from(expectedObjects), + as(expectedObjects), compare ); }); @@ -56,13 +56,13 @@ import { map, toNodeStream } from 'ix/asynciterable/operators/index.node'; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { await expect(stringsItr().pipe(toNodeStream({ objectMode: false }))).toEqualStream( - from(expectedStrings), + as(expectedStrings), compare ); }); test('yields Buffers', async () => { await expect(buffersItr().pipe(toNodeStream({ objectMode: false }))).toEqualStream( - from(expectedBuffers), + as(expectedBuffers), compare ); }); diff --git a/spec/asynciterable/toobservable-spec.ts b/spec/asynciterable/toobservable-spec.ts index ff634034..6be3e372 100644 --- a/spec/asynciterable/toobservable-spec.ts +++ b/spec/asynciterable/toobservable-spec.ts @@ -1,6 +1,6 @@ import '../asynciterablehelpers'; -import Ix from 'ix/Ix'; -import { empty, from, of, throwError, toArray, toObservable } from 'ix/asynciterable'; +import { symbolObservable } from 'ix/Ix'; +import { empty, as, of, throwError, toArray, toObservable } from 'ix/asynciterable'; import { Observable as RxJSObservable, from as RxJSObservableFrom } from 'rxjs'; import { Observable, PartialObserver } from '../../src/observer'; @@ -62,10 +62,10 @@ test('AsyncIterable#toObservable error', async () => { }); }); -test('AsyncIterable#toObservable Symbol.observable should return same instance', async () => { +test('AsyncIterable#toObservable Symbol.observable should return same instance', () => { const ys = toObservable(of(1, 2, 3)); // @ts-ignore - expect(ys).toBe(ys[Ix.symbolObservable]()); + expect(ys).toBe(ys[symbolObservable]()); }); test('AsyncIterable#toObservable accepts partial observers', async () => { @@ -93,7 +93,7 @@ test('AsyncIterable#toObservable accepts partial observers', async () => { expect(actualValues).toEqual(expectedValues); expect(actualError).toEqual(expectedError); - expect(completeCalled).toEqual(true); + expect(completeCalled).toBe(true); }); test('AsyncIterable#toObservable accepts observer functions', async () => { @@ -121,7 +121,7 @@ test('AsyncIterable#toObservable accepts observer functions', async () => { expect(actualValues).toEqual(expectedValues); expect(actualError).toEqual(expectedError); - expect(completeCalled).toEqual(true); + expect(completeCalled).toBe(true); }); test('AsyncIterable#toObservable interop with rxjs', async () => { @@ -132,7 +132,7 @@ test('AsyncIterable#toObservable interop with rxjs', async () => { }); test('AsyncIterable.from interop with rxjs', async () => { - const ys = from(RxJSObservableFrom(toObservable(of(1, 2, 3)))); + const ys = as(RxJSObservableFrom(toObservable(of(1, 2, 3)))); const xs = await toArray(ys); expect(xs).toEqual([1, 2, 3]); }); @@ -155,16 +155,16 @@ function endOfObservable( }; if (next && typeof next === 'object') { // prettier-ignore - next.error = wrap(e => reject(e),(next.error || (() => { /**/ })).bind(next)); + next.error = wrap(e => reject(e), (next.error || (() => { /**/ })).bind(next)); // prettier-ignore next.complete = wrap(() => resolve(), (next.complete || (() => { /**/ })).bind(next)); } else { // prettier-ignore // eslint-disable-next-line no-param-reassign - error = wrap(e => reject(e),error || (() => { /**/ })); + error = wrap(e => reject(e), error || (() => { /**/ })); // prettier-ignore // eslint-disable-next-line no-param-reassign - complete = wrap(() => resolve(),complete || (() => { /**/ })); + complete = wrap(() => resolve(), complete || (() => { /**/ })); } observable.subscribe(next, error, complete); diff --git a/spec/asynciterable/toset-spec.ts b/spec/asynciterable/toset-spec.ts index 26bea447..e45e1eb7 100644 --- a/spec/asynciterable/toset-spec.ts +++ b/spec/asynciterable/toset-spec.ts @@ -1,10 +1,10 @@ import '../asynciterablehelpers'; -import { empty, from, toSet } from 'ix/asynciterable'; +import { empty, as, toSet } from 'ix/asynciterable'; import { sequenceEqual } from 'ix/iterable'; test('AsyncIterable#toSet non-empty', async () => { const xs = [1, 2, 3, 4, 5]; - const ys = from(xs); + const ys = as(xs); const res = await toSet(ys); expect(sequenceEqual(res, xs)).toBeTruthy(); }); @@ -16,7 +16,7 @@ test('AsyncIterable#toSet empty', async () => { }); test('AsyncIterable#toSet trims', async () => { - const xs = from([1, 2, 3, 3, 2, 1]); + const xs = as([1, 2, 3, 3, 2, 1]); const ys = [1, 2, 3]; const res = await toSet(xs); expect(sequenceEqual(res, ys)).toBeTruthy(); diff --git a/spec/asynciterablehelpers.ts b/spec/asynciterablehelpers.ts index db59ea70..a46997a9 100644 --- a/spec/asynciterablehelpers.ts +++ b/spec/asynciterablehelpers.ts @@ -1,5 +1,5 @@ import './Ix'; -import { from } from 'ix/asynciterable'; +import { AsyncIterableX } from 'ix/asynciterable'; import { Observer, PartialObserver } from '../src/observer'; export async function hasNext(source: AsyncIterator, expected: T) { @@ -81,7 +81,7 @@ expect.extend({ let next1: IteratorResult; let next2: IteratorResult; const results: string[] = []; - const it1 = from(expected)[Symbol.asyncIterator](); + const it1 = AsyncIterableX.as(expected)[Symbol.asyncIterator](); const it2 = typeof (actual)[Symbol.asyncIterator] === 'function' ? (actual)[Symbol.asyncIterator]() diff --git a/spec/iterable-operators/groupby-spec.ts b/spec/iterable-operators/groupby-spec.ts index b58c2e42..64f8ecd1 100644 --- a/spec/iterable-operators/groupby-spec.ts +++ b/spec/iterable-operators/groupby-spec.ts @@ -1,5 +1,5 @@ import { hasNext, noNext } from '../iterablehelpers'; -import { from, empty } from 'ix/iterable'; +import { as, empty } from 'ix/iterable'; import { groupBy } from 'ix/iterable/operators'; test('Iterable#groupBy normal', () => { @@ -12,7 +12,7 @@ test('Iterable#groupBy normal', () => { { name: 'Lisa', age: 23 }, { name: 'Eric', age: 42 }, ]; - const ys = from(xs).pipe(groupBy((x) => Math.floor(x.age / 10))); + const ys = as(xs).pipe(groupBy((x) => Math.floor(x.age / 10))); const it = ys[Symbol.iterator](); let next = it.next(); @@ -59,7 +59,7 @@ test('Iterable#groupBy normal can get results later', () => { { name: 'Lisa', age: 23 }, { name: 'Eric', age: 42 }, ]; - const ys = from(xs).pipe(groupBy((x) => Math.floor(x.age / 10))); + const ys = as(xs).pipe(groupBy((x) => Math.floor(x.age / 10))); const it = ys[Symbol.iterator](); const g1 = it.next(); @@ -110,7 +110,7 @@ test('Iterable#groupBy empty', () => { test('Iterable#groupBy element selector', () => { const xs = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]; - const ys = from(xs).pipe( + const ys = as(xs).pipe( groupBy( (x) => x % 3, (x) => String.fromCharCode(97 + x) diff --git a/spec/iterable-operators/groupjoin-spec.ts b/spec/iterable-operators/groupjoin-spec.ts index 2d8bda10..f1843412 100644 --- a/spec/iterable-operators/groupjoin-spec.ts +++ b/spec/iterable-operators/groupjoin-spec.ts @@ -1,11 +1,11 @@ import { hasNext, noNext } from '../iterablehelpers'; import { groupJoin } from 'ix/iterable/operators'; -import { from, reduce, throwError } from 'ix/iterable'; +import { as, reduce, throwError } from 'ix/iterable'; test('Iterable#groupJoin all groups have values', () => { const xs = [0, 1, 2]; const ys = [4, 7, 6, 2, 3, 4, 8, 9]; - const res = from(xs).pipe( + const res = as(xs).pipe( groupJoin( ys, (x) => x % 3, @@ -24,7 +24,7 @@ test('Iterable#groupJoin all groups have values', () => { test('Iterable#groupJoin some groups have values', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( groupJoin( ys, (x) => x % 3, @@ -43,7 +43,7 @@ test('Iterable#groupJoin some groups have values', () => { test('Iterable#groupJoin left throws', () => { const xs = throwError(new Error()); const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( groupJoin( ys, (x) => x % 3, @@ -59,7 +59,7 @@ test('Iterable#groupJoin left throws', () => { test('Iterable#groupJoin right throws', () => { const xs = [0, 1, 2]; const ys = throwError(new Error()); - const res = from(xs).pipe( + const res = as(xs).pipe( groupJoin( ys, (x) => x % 3, @@ -75,7 +75,7 @@ test('Iterable#groupJoin right throws', () => { test('Iterable#groupJoin left selector throws', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( groupJoin( ys, (_) => { @@ -93,7 +93,7 @@ test('Iterable#groupJoin left selector throws', () => { test('Iterable#groupJoin right selector throws', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( groupJoin( ys, (x) => x % 3, @@ -111,7 +111,7 @@ test('Iterable#groupJoin right selector throws', () => { test('Iterable#groupJoin result selector eventually throws', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( groupJoin( ys, (x) => x % 3, diff --git a/spec/iterable-operators/innerjoin-spec.ts b/spec/iterable-operators/innerjoin-spec.ts index 8cb68181..b5e12945 100644 --- a/spec/iterable-operators/innerjoin-spec.ts +++ b/spec/iterable-operators/innerjoin-spec.ts @@ -1,11 +1,11 @@ import { hasNext, noNext } from '../iterablehelpers'; -import { from, throwError } from 'ix/iterable'; +import { as, throwError } from 'ix/iterable'; import { innerJoin } from 'ix/iterable/operators'; test('Iterable#innerJoin normal', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, @@ -24,7 +24,7 @@ test('Iterable#innerJoin normal', () => { test('Iterable#innerJoin reversed', () => { const xs = [3, 6, 4]; const ys = [0, 1, 2]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, @@ -43,7 +43,7 @@ test('Iterable#innerJoin reversed', () => { test('Iterable#innerJoin only one group matches', () => { const xs = [0, 1, 2]; const ys = [3, 6]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, @@ -61,7 +61,7 @@ test('Iterable#innerJoin only one group matches', () => { test('Iterable#innerJoin only one group matches reversed', () => { const xs = [3, 6]; const ys = [0, 1, 2]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, @@ -79,7 +79,7 @@ test('Iterable#innerJoin only one group matches reversed', () => { test('Iterable#innerJoin left throws', () => { const xs = throwError(new Error()); const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, @@ -95,7 +95,7 @@ test('Iterable#innerJoin left throws', () => { test('Iterable#innerJoin right throws', () => { const xs = [0, 1, 2]; const ys = throwError(new Error()); - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, @@ -111,7 +111,7 @@ test('Iterable#innerJoin right throws', () => { test('Iterable#innerJoin left selector throws', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (_) => { @@ -129,7 +129,7 @@ test('Iterable#innerJoin left selector throws', () => { test('Iterable#join right selector throws', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, @@ -147,7 +147,7 @@ test('Iterable#join right selector throws', () => { test('Iterable#innerJoin result selector throws', () => { const xs = [0, 1, 2]; const ys = [3, 6, 4]; - const res = from(xs).pipe( + const res = as(xs).pipe( innerJoin( ys, (x) => x % 3, diff --git a/spec/iterable-operators/intersect-spec.ts b/spec/iterable-operators/intersect-spec.ts index 600ba9c0..1e736719 100644 --- a/spec/iterable-operators/intersect-spec.ts +++ b/spec/iterable-operators/intersect-spec.ts @@ -1,11 +1,11 @@ import { hasNext, noNext } from '../iterablehelpers'; -import { from } from 'ix/iterable'; +import { as } from 'ix/iterable'; import { intersect } from 'ix/iterable/operators'; test('Iterable#union with default comparer', () => { const xs = [1, 2, 3]; const ys = [3, 5, 1, 4]; - const res = from(xs).pipe(intersect(ys)); + const res = as(xs).pipe(intersect(ys)); const it = res[Symbol.iterator](); hasNext(it, 1); @@ -17,7 +17,7 @@ test('Iterable#union with custom comparer', () => { const comparer = (x: number, y: number) => Math.abs(x) === Math.abs(y); const xs = [1, 2, -3]; const ys = [3, 5, -1, 4]; - const res = from(xs).pipe(intersect(ys, comparer)); + const res = as(xs).pipe(intersect(ys, comparer)); const it = res[Symbol.iterator](); hasNext(it, 1); diff --git a/spec/iterable-operators/map-spec.ts b/spec/iterable-operators/map-spec.ts index 5f413eed..71c29fd5 100644 --- a/spec/iterable-operators/map-spec.ts +++ b/spec/iterable-operators/map-spec.ts @@ -1,12 +1,12 @@ import '../iterablehelpers'; -import { from, empty, sequenceEqual } from 'ix/iterable'; +import { as, empty, sequenceEqual } from 'ix/iterable'; import { map } from 'ix/iterable/operators'; test('Iterable#map single element', () => { const source = [{ name: 'Frank', custId: 98088 }]; const expected = ['Frank']; - expect(sequenceEqual(expected, from(source).pipe(map((x) => x.name)))).toBeTruthy(); + expect(sequenceEqual(expected, as(source).pipe(map((x) => x.name)))).toBeTruthy(); }); test('Iterable#map maps property', () => { @@ -19,7 +19,7 @@ test('Iterable#map maps property', () => { ]; const expected = ['Frank', 'Bob', 'Chris', null, 'Frank']; - expect(sequenceEqual(expected, from(source).pipe(map((x) => x.name)))).toBeTruthy(); + expect(sequenceEqual(expected, as(source).pipe(map((x) => x.name)))).toBeTruthy(); }); test('Iterable#map empty', () => { @@ -37,7 +37,7 @@ test('Iterable#map map property using index', () => { const expected = ['Frank', null, null]; expect( - sequenceEqual(expected, from(source).pipe(map((x, i) => (i === 0 ? x.name : null)))) + sequenceEqual(expected, as(source).pipe(map((x, i) => (i === 0 ? x.name : null)))) ).toBeTruthy(); }); @@ -52,7 +52,7 @@ test('Iterable#map map property using index on last', () => { const expected = [null, null, null, null, 'Frank']; expect( - sequenceEqual(expected, from(source).pipe(map((x, i) => (i === 4 ? x.name : null)))) + sequenceEqual(expected, as(source).pipe(map((x, i) => (i === 4 ? x.name : null)))) ).toBeTruthy(); }); @@ -65,7 +65,7 @@ test('Iterable#map execution is deferred', () => { }, ]; - from(source).pipe(map((x) => x())); + as(source).pipe(map((x) => x())); expect(fnCalled).toBeFalsy(); }); diff --git a/spec/iterable-operators/orderby-spec.ts b/spec/iterable-operators/orderby-spec.ts index 4c71e68f..7d1bc325 100644 --- a/spec/iterable-operators/orderby-spec.ts +++ b/spec/iterable-operators/orderby-spec.ts @@ -1,10 +1,10 @@ import { hasNext, noNext } from '../iterablehelpers'; -import { from } from 'ix/iterable'; +import { as } from 'ix/iterable'; import { orderBy, orderByDescending, thenBy, thenByDescending } from 'ix/iterable/operators'; test('Iterable#orderBy normal ordering', () => { const xs = [2, 6, 1, 5, 7, 8, 9, 3, 4, 0]; - const ys = from(xs).pipe(orderBy((x) => x)); + const ys = as(xs).pipe(orderBy((x) => x)); const it = ys[Symbol.iterator](); for (let i = 0; i < 10; i++) { @@ -16,7 +16,7 @@ test('Iterable#orderBy normal ordering', () => { test('Iterable#orderBy normal ordering with thenBy throws', () => { const xs = [2, 6, 1, 5, 7, 8, 9, 3, 4, 0]; - const ys = from(xs) + const ys = as(xs) .pipe(orderBy((x) => x)) .pipe( thenBy(() => { @@ -30,7 +30,7 @@ test('Iterable#orderBy normal ordering with thenBy throws', () => { test('Iterable#orderBy selector throws', () => { const xs = [2, 6, 1, 5, 7, 8, 9, 3, 4, 0]; - const ys = from(xs).pipe( + const ys = as(xs).pipe( orderBy(() => { throw new Error(); }) @@ -42,7 +42,7 @@ test('Iterable#orderBy selector throws', () => { test('Iterable#orderByDescending normal ordering', () => { const xs = [2, 6, 1, 5, 7, 8, 9, 3, 4, 0]; - const ys = from(xs).pipe(orderByDescending((x) => x)); + const ys = as(xs).pipe(orderByDescending((x) => x)); const it = ys[Symbol.iterator](); for (let i = 9; i >= 0; i--) { @@ -54,7 +54,7 @@ test('Iterable#orderByDescending normal ordering', () => { test('Iterable#orderByDescending normal ordering with thenByDescending throws', () => { const xs = [2, 6, 1, 5, 7, 8, 9, 3, 4, 0]; - const ys = from(xs) + const ys = as(xs) .pipe(orderByDescending((x) => x)) .pipe( thenByDescending(() => { diff --git a/spec/iterable-operators/pairwise-spec.ts b/spec/iterable-operators/pairwise-spec.ts index fffebb89..f1396a74 100644 --- a/spec/iterable-operators/pairwise-spec.ts +++ b/spec/iterable-operators/pairwise-spec.ts @@ -1,10 +1,10 @@ import { hasNext, noNext } from '../iterablehelpers'; import { pairwise } from 'ix/iterable/operators'; -import { from, empty, of } from 'ix/iterable'; +import { as, empty, of } from 'ix/iterable'; test('Iterable#pairwise empty return empty', () => { const xs = empty(); - const ys = from(xs).pipe(pairwise()); + const ys = as(xs).pipe(pairwise()); const it = ys[Symbol.iterator](); noNext(it); @@ -12,7 +12,7 @@ test('Iterable#pairwise empty return empty', () => { test('Iterable#pairwise single returns empty', () => { const xs = of(5); - const ys = from(xs).pipe(pairwise()); + const ys = as(xs).pipe(pairwise()); const it = ys[Symbol.iterator](); noNext(it); @@ -20,7 +20,7 @@ test('Iterable#pairwise single returns empty', () => { test('Iterable#pairwise behavior', () => { const xs = of(5, 4, 3, 2, 1); - const ys = from(xs).pipe(pairwise()); + const ys = as(xs).pipe(pairwise()); const it = ys[Symbol.iterator](); hasNext(it, [5, 4]); diff --git a/spec/iterable-operators/pluck-spec.ts b/spec/iterable-operators/pluck-spec.ts index e8b1915b..c9671b6f 100644 --- a/spec/iterable-operators/pluck-spec.ts +++ b/spec/iterable-operators/pluck-spec.ts @@ -1,10 +1,10 @@ import { hasNext, noNext } from '../iterablehelpers'; import { pluck } from 'ix/iterable/operators'; -import { from, of } from 'ix/iterable'; +import { as, of } from 'ix/iterable'; test('Iterable#pluck simple prop', () => { const xs = of({ prop: 1 }, { prop: 2 }, { prop: 3 }, { prop: 4 }, { prop: 5 }); - const ys = from(xs).pipe(pluck('prop')); + const ys = as(xs).pipe(pluck('prop')); const it = ys[Symbol.iterator](); hasNext(it, 1); @@ -23,7 +23,7 @@ test('Iterable#pluck nested prop', () => { { a: { b: { c: 4 } } }, { a: { b: { c: 5 } } } ); - const ys = from(xs).pipe(pluck('a', 'b', 'c')); + const ys = as(xs).pipe(pluck('a', 'b', 'c')); const it = ys[Symbol.iterator](); hasNext(it, 1); @@ -42,7 +42,7 @@ test('Iterable#pluck edge cases', () => { {}, { a: { b: { c: 5 } } } ); - const ys = from(xs).pipe(pluck('a', 'b', 'c')); + const ys = as(xs).pipe(pluck('a', 'b', 'c')); const it = ys[Symbol.iterator](); hasNext(it, 1); diff --git a/spec/iterable-operators/repeat-spec.ts b/spec/iterable-operators/repeat-spec.ts index 029773f9..0a29581a 100644 --- a/spec/iterable-operators/repeat-spec.ts +++ b/spec/iterable-operators/repeat-spec.ts @@ -1,10 +1,10 @@ import '../iterablehelpers'; -import { from, every, sum, toArray } from 'ix/iterable'; +import { as, every, sum, toArray } from 'ix/iterable'; import { buffer, map, take, tap, repeat } from 'ix/iterable/operators'; test('Iterable#repeat infinite', () => { let i = 0; - const xs = from([1, 2]) + const xs = as([1, 2]) .pipe(tap({ next: () => ++i })) .pipe(repeat()); @@ -12,7 +12,7 @@ test('Iterable#repeat infinite', () => { expect(10).toBe(res.length); expect( every( - from(res) + as(res) .pipe(buffer(2)) .pipe(map((b) => sum(b))), { predicate: (x) => x === 3 } @@ -23,7 +23,7 @@ test('Iterable#repeat infinite', () => { test('Iterable#repeat finite', () => { let i = 0; - const xs = from([1, 2]) + const xs = as([1, 2]) .pipe(tap({ next: () => ++i })) .pipe(repeat(5)); @@ -31,7 +31,7 @@ test('Iterable#repeat finite', () => { expect(10).toBe(res.length); expect( every( - from(res) + as(res) .pipe(buffer(2)) .pipe(map((b) => sum(b))), { predicate: (x) => x === 3 } diff --git a/spec/iterable-operators/skip-spec.ts b/spec/iterable-operators/skip-spec.ts index b85ef0e1..5183172b 100644 --- a/spec/iterable-operators/skip-spec.ts +++ b/spec/iterable-operators/skip-spec.ts @@ -1,10 +1,10 @@ import { hasNext, noNext } from '../iterablehelpers'; -import { from, throwError } from 'ix/iterable'; +import { as, throwError } from 'ix/iterable'; import { skip } from 'ix/iterable/operators'; test('Iterable#skip skips some', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(skip(2)); + const ys = as(xs).pipe(skip(2)); const it = ys[Symbol.iterator](); hasNext(it, 3); @@ -14,7 +14,7 @@ test('Iterable#skip skips some', () => { test('Iterable#skip skips more than count', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(skip(10)); + const ys = as(xs).pipe(skip(10)); const it = ys[Symbol.iterator](); noNext(it); @@ -22,7 +22,7 @@ test('Iterable#skip skips more than count', () => { test('Iterable#skip none', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(skip(0)); + const ys = as(xs).pipe(skip(0)); const it = ys[Symbol.iterator](); hasNext(it, 1); @@ -34,7 +34,7 @@ test('Iterable#skip none', () => { test('Iterable#skip throws', () => { const xs = throwError(new Error()); - const ys = from(xs).pipe(skip(2)); + const ys = as(xs).pipe(skip(2)); const it = ys[Symbol.iterator](); expect(() => it.next()).toThrow(); diff --git a/spec/iterable-operators/skipwhile-spec.ts b/spec/iterable-operators/skipwhile-spec.ts index db7e7321..fca8737e 100644 --- a/spec/iterable-operators/skipwhile-spec.ts +++ b/spec/iterable-operators/skipwhile-spec.ts @@ -1,10 +1,10 @@ import { hasNext, noNext } from '../iterablehelpers'; import { skipWhile } from 'ix/iterable/operators'; -import { from } from 'ix/iterable'; +import { as } from 'ix/iterable'; test('Iterable#skipWhile skips some', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(skipWhile((x) => x < 3)); + const ys = as(xs).pipe(skipWhile((x) => x < 3)); const it = ys[Symbol.iterator](); hasNext(it, 3); @@ -14,7 +14,7 @@ test('Iterable#skipWhile skips some', () => { test('Iterable#skipWhile skips none', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(skipWhile(() => false)); + const ys = as(xs).pipe(skipWhile(() => false)); const it = ys[Symbol.iterator](); hasNext(it, 1); @@ -26,7 +26,7 @@ test('Iterable#skipWhile skips none', () => { test('Iterable#skipWhile skips all', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(skipWhile(() => true)); + const ys = as(xs).pipe(skipWhile(() => true)); const it = ys[Symbol.iterator](); noNext(it); @@ -34,7 +34,7 @@ test('Iterable#skipWhile skips all', () => { test('Iterable#skipWhile skips some another run', () => { const xs = [1, 2, 3, 4, 3, 2, 1]; - const ys = from(xs).pipe(skipWhile((x) => x < 3)); + const ys = as(xs).pipe(skipWhile((x) => x < 3)); const it = ys[Symbol.iterator](); hasNext(it, 3); @@ -47,7 +47,7 @@ test('Iterable#skipWhile skips some another run', () => { test('Iterable#skipWhile predicate throws', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe( + const ys = as(xs).pipe( skipWhile(() => { throw new Error(); }) @@ -59,7 +59,7 @@ test('Iterable#skipWhile predicate throws', () => { test('Iterable#skipWhile with index', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(skipWhile((_, i) => i < 2)); + const ys = as(xs).pipe(skipWhile((_, i) => i < 2)); const it = ys[Symbol.iterator](); hasNext(it, 3); diff --git a/spec/iterable-operators/slice-spec.ts b/spec/iterable-operators/slice-spec.ts index 3eb6c5ac..37519606 100644 --- a/spec/iterable-operators/slice-spec.ts +++ b/spec/iterable-operators/slice-spec.ts @@ -1,10 +1,10 @@ import { hasNext, noNext } from '../iterablehelpers'; import { slice } from 'ix/iterable/operators'; -import { from } from 'ix/iterable'; +import { as } from 'ix/iterable'; test('Iterable#slice slices at zero with one item', () => { - const xs = from([1, 2, 3, 4]); - const ys = from(xs).pipe(slice(0, 1)); + const xs = as([1, 2, 3, 4]); + const ys = as(xs).pipe(slice(0, 1)); const it = ys[Symbol.iterator](); hasNext(it, 1); @@ -12,8 +12,8 @@ test('Iterable#slice slices at zero with one item', () => { }); test('Iterable#slice slices at one with one item', () => { - const xs = from([1, 2, 3, 4]); - const ys = from(xs).pipe(slice(1, 1)); + const xs = as([1, 2, 3, 4]); + const ys = as(xs).pipe(slice(1, 1)); const it = ys[Symbol.iterator](); hasNext(it, 2); @@ -21,8 +21,8 @@ test('Iterable#slice slices at one with one item', () => { }); test('Iterable#slice slices at one with multiple items', () => { - const xs = from([1, 2, 3, 4]); - const ys = from(xs).pipe(slice(1, 2)); + const xs = as([1, 2, 3, 4]); + const ys = as(xs).pipe(slice(1, 2)); const it = ys[Symbol.iterator](); hasNext(it, 2); @@ -31,8 +31,8 @@ test('Iterable#slice slices at one with multiple items', () => { }); test('Iterable#slice slices at one with no end', () => { - const xs = from([1, 2, 3, 4]); - const ys = from(xs).pipe(slice(1)); + const xs = as([1, 2, 3, 4]); + const ys = as(xs).pipe(slice(1)); const it = ys[Symbol.iterator](); hasNext(it, 2); @@ -42,8 +42,8 @@ test('Iterable#slice slices at one with no end', () => { }); test('Iterable#slice slices at zero with no end', () => { - const xs = from([1, 2, 3, 4]); - const ys = from(xs).pipe(slice(0)); + const xs = as([1, 2, 3, 4]); + const ys = as(xs).pipe(slice(0)); const it = ys[Symbol.iterator](); hasNext(it, 1); diff --git a/spec/iterable-operators/takewhile-spec.ts b/spec/iterable-operators/takewhile-spec.ts index 572ae440..45d61f27 100644 --- a/spec/iterable-operators/takewhile-spec.ts +++ b/spec/iterable-operators/takewhile-spec.ts @@ -1,10 +1,10 @@ import { hasNext, noNext } from '../iterablehelpers'; import { takeWhile } from 'ix/iterable/operators'; -import { from } from 'ix/iterable'; +import { as } from 'ix/iterable'; test('Iterable#takeWhile some match', () => { const xs = [1, 2, 3, 4]; - const ys = from(xs).pipe(takeWhile((x) => x < 3)); + const ys = as(xs).pipe(takeWhile((x) => x < 3)); const it = ys[Symbol.iterator](); hasNext(it, 1); diff --git a/spec/iterable/as-spec.ts b/spec/iterable/as-spec.ts index ee507656..e9131449 100644 --- a/spec/iterable/as-spec.ts +++ b/spec/iterable/as-spec.ts @@ -1,9 +1,9 @@ import { hasNext, noNext } from '../iterablehelpers'; -import { as } from 'ix/iterable'; +import { IterableX } from 'ix/iterable'; test('Iterable#as from array/iterable', () => { const xs = [1, 2, 3]; - const res = as(xs); + const res = IterableX.as(xs); const it = res[Symbol.iterator](); hasNext(it, 1); @@ -14,7 +14,7 @@ test('Iterable#as from array/iterable', () => { test('Iterable#as from empty array/iterable', () => { const xs: number[] = []; - const res = as(xs); + const res = IterableX.as(xs); const it = res[Symbol.iterator](); noNext(it); @@ -22,7 +22,7 @@ test('Iterable#as from empty array/iterable', () => { test('Iterable#as from array-like', () => { const xs = { length: 3 }; - const res = as(xs); + const res = IterableX.as(xs); const it = res[Symbol.iterator](); hasNext(it, undefined); @@ -33,7 +33,7 @@ test('Iterable#as from array-like', () => { test('Iterable#as from non-iterable', () => { const xs = {}; - const res = as(xs); + const res = IterableX.as(xs); const it = res[Symbol.iterator](); hasNext(it, xs); diff --git a/spec/iterable/todomstream-spec.ts b/spec/iterable/todomstream-spec.ts index 40112c0f..17239b99 100644 --- a/spec/iterable/todomstream-spec.ts +++ b/spec/iterable/todomstream-spec.ts @@ -1,6 +1,6 @@ import '../iterablehelpers'; import '../asynciterablehelpers'; -import { from } from 'ix/iterable'; +import { as } from 'ix/iterable'; import { map, toDOMStream } from 'ix/iterable/operators'; // eslint-disable-next-line consistent-return @@ -11,7 +11,7 @@ import { map, toDOMStream } from 'ix/iterable/operators'; }); } - const stringsItr = () => from([1, 2, 3]).pipe(map((i) => `${i}`)); + const stringsItr = () => as([1, 2, 3]).pipe(map((i) => `${i}`)); const buffersItr = () => stringsItr().pipe(map((val) => Buffer.from(val))); const objectsItr = () => stringsItr().pipe(map((val) => ({ val }))); const compare = (a: T, b: T) => { @@ -32,17 +32,17 @@ import { map, toDOMStream } from 'ix/iterable/operators'; const expectedObjects = expectedStrings.map((val) => ({ val })); const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { - const expected = from(expectedStrings); + const expected = as(expectedStrings); const actual = stringsItr().pipe(toDOMStream()); await expect(actual).toEqualStream(expected, compare); }); test('yields Buffers', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = buffersItr().pipe(toDOMStream()); await expect(actual).toEqualStream(expected, compare); }); test('yields Objects', async () => { - const expected = from(expectedObjects); + const expected = as(expectedObjects); const actual = objectsItr().pipe(toDOMStream()); await expect(actual).toEqualStream(expected, compare); }); @@ -52,14 +52,14 @@ import { map, toDOMStream } from 'ix/iterable/operators'; const expectedStrings = ['123']; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = stringsItr() .pipe(map((x) => Buffer.from(x))) .pipe(toDOMStream({ type: 'bytes' })); await expect(actual).toEqualStream(expected, compare); }); test('yields Buffers', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = buffersItr().pipe(toDOMStream({ type: 'bytes' })); await expect(actual).toEqualStream(expected, compare); }); @@ -69,14 +69,14 @@ import { map, toDOMStream } from 'ix/iterable/operators'; const expectedStrings = ['123']; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = stringsItr() .pipe(map((x) => Buffer.from(x))) .pipe(toDOMStream({ type: 'bytes', autoAllocateChunkSize: 1024 })); await expect(actual).toEqualStream(expected, compare); }); test('yields Buffers', async () => { - const expected = from(expectedBuffers); + const expected = as(expectedBuffers); const actual = buffersItr().pipe( toDOMStream({ type: 'bytes', autoAllocateChunkSize: 1024 }) ); diff --git a/spec/iterable/tonodestream-spec.ts b/spec/iterable/tonodestream-spec.ts index e3ca913f..c7941d86 100644 --- a/spec/iterable/tonodestream-spec.ts +++ b/spec/iterable/tonodestream-spec.ts @@ -1,7 +1,7 @@ import '../iterablehelpers'; import '../asynciterablehelpers'; -import { from as fromIterable } from 'ix/iterable'; -import { from as fromAsyncIterable } from 'ix/asynciterable'; +import { as as asIterable } from 'ix/iterable'; +import { as as asAsyncIterable } from 'ix/asynciterable'; import { map, toNodeStream } from 'ix/iterable/operators/index.node'; import { IterableReadable } from 'ix/Ix.node'; @@ -13,7 +13,7 @@ import { IterableReadable } from 'ix/Ix.node'; }); } - const stringsItr = () => fromIterable([1, 2, 3]).pipe(map((i) => `${i}`)); + const stringsItr = () => asIterable([1, 2, 3]).pipe(map((i) => `${i}`)); const buffersItr = () => stringsItr().pipe(map((val) => Buffer.from(val))); const objectsItr = () => stringsItr().pipe(map((val) => ({ val }))); const compare = (a: T, b: T) => { @@ -35,19 +35,19 @@ import { IterableReadable } from 'ix/Ix.node'; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { await expect(stringsItr().pipe(toNodeStream({ objectMode: true }))).toEqualStream( - fromAsyncIterable(expectedStrings), + asAsyncIterable(expectedStrings), compare ); }); test('yields Buffers', async () => { await expect(buffersItr().pipe(toNodeStream({ objectMode: true }))).toEqualStream( - fromAsyncIterable(expectedBuffers), + asAsyncIterable(expectedBuffers), compare ); }); test('yields Objects', async () => { await expect(objectsItr().pipe(toNodeStream({ objectMode: true }))).toEqualStream( - fromAsyncIterable(expectedObjects), + asAsyncIterable(expectedObjects), compare ); }); @@ -58,13 +58,13 @@ import { IterableReadable } from 'ix/Ix.node'; const expectedBuffers = expectedStrings.map((x) => Buffer.from(x)); test('yields Strings', async () => { await expect(stringsItr().pipe(toNodeStream({ objectMode: false }))).toEqualStream( - fromAsyncIterable(expectedStrings), + asAsyncIterable(expectedStrings), compare ); }); test('yields Buffers', async () => { await expect(buffersItr().pipe(toNodeStream({ objectMode: false }))).toEqualStream( - fromAsyncIterable(expectedBuffers), + asAsyncIterable(expectedBuffers), compare ); }); diff --git a/spec/tsconfig/tsconfig.es2015.umd.json b/spec/tsconfig/tsconfig.es2015.umd.json index 5f848e3b..d87f05d6 100644 --- a/spec/tsconfig/tsconfig.es2015.umd.json +++ b/spec/tsconfig/tsconfig.es2015.umd.json @@ -7,10 +7,11 @@ "declaration": false, "noEmitHelpers": true, "importHelpers": true, + "esModuleInterop": true, "paths": { "ix/*": [ "targets/es2015/umd/*" ] } } -} \ No newline at end of file +} diff --git a/spec/tsconfig/tsconfig.es5.umd.json b/spec/tsconfig/tsconfig.es5.umd.json index 6cffe61c..97eae36d 100644 --- a/spec/tsconfig/tsconfig.es5.umd.json +++ b/spec/tsconfig/tsconfig.es5.umd.json @@ -7,6 +7,7 @@ "declaration": false, "noEmitHelpers": true, "importHelpers": true, + "esModuleInterop": true, "downlevelIteration": true, "paths": { "ix/*": [ @@ -14,4 +15,4 @@ ] } } -} \ No newline at end of file +} diff --git a/spec/tsconfig/tsconfig.esnext.umd.json b/spec/tsconfig/tsconfig.esnext.umd.json index 76b627d4..9cc69006 100644 --- a/spec/tsconfig/tsconfig.esnext.umd.json +++ b/spec/tsconfig/tsconfig.esnext.umd.json @@ -7,10 +7,11 @@ "declaration": false, "noEmitHelpers": true, "importHelpers": true, + "esModuleInterop": true, "paths": { "ix/*": [ "targets/esnext/umd/*" ] } } -} \ No newline at end of file +} diff --git a/src/Ix.node.ts b/src/Ix.node.ts index 18a96075..d021c71e 100644 --- a/src/Ix.node.ts +++ b/src/Ix.node.ts @@ -89,14 +89,12 @@ import './add/asynciterable-operators/toset'; import './add/asynciterable-operators/union'; import './add/asynciterable-operators/withlatestfrom'; import './add/asynciterable-operators/zip'; -import './add/iterable/as'; import './add/iterable/catchall'; import './add/iterable/catcherror'; import './add/iterable/concat'; import './add/iterable/create'; import './add/iterable/defer'; import './add/iterable/empty'; -import './add/iterable/from'; import './add/iterable/generate'; import './add/iterable/iif'; import './add/iterable/of'; @@ -175,7 +173,6 @@ import './add/iterable-operators/tonodestream'; import './add/iterable-operators/toset'; import './add/iterable-operators/union'; import './add/iterable-operators/zip'; -import './add/asynciterable/as'; import './add/asynciterable/asyncifyerrback'; import './add/asynciterable/asyncify'; import './add/asynciterable/catchall'; @@ -190,7 +187,6 @@ import './add/asynciterable/fromdomstream'; import './add/asynciterable/fromeventpattern'; import './add/asynciterable/fromevent'; import './add/asynciterable/fromnodestream'; -import './add/asynciterable/from'; import './add/asynciterable/generatetime'; import './add/asynciterable/generate'; import './add/asynciterable/iif'; diff --git a/src/Ix.ts b/src/Ix.ts index 3c8187ec..cdd0c301 100644 --- a/src/Ix.ts +++ b/src/Ix.ts @@ -1,8 +1,7 @@ import { AbortError } from './aborterror'; -import { AsyncSink } from './asynciterable/asyncsink'; import { IterableX } from './iterable/iterablex'; import { observable } from './observer'; -import { AsyncIterableX } from './asynciterable/asynciterablex'; +import { AsyncIterableX, AsyncSink } from './asynciterable/asynciterablex'; import { GroupedIterable as ImportedGroupedIterable } from './iterable/operators/groupby'; import { GroupedAsyncIterable as ImportedGroupedAsyncIterable } from './asynciterable/operators/groupby'; export { OrderedIterableX as OrderedIterable } from './iterable/operators/orderby'; diff --git a/src/add/asynciterable-operators/switchmap.ts b/src/add/asynciterable-operators/switchmap.ts index c4d0d74a..365dd206 100644 --- a/src/add/asynciterable-operators/switchmap.ts +++ b/src/add/asynciterable-operators/switchmap.ts @@ -4,7 +4,7 @@ import { switchMap } from '../../asynciterable/operators/switchmap'; /** * @ignore */ -export function switchMapProto>( +export function switchMapProto>( this: AsyncIterableX, selector: (value: T, index: number, signal?: AbortSignal) => R | Promise, thisArg?: any diff --git a/src/add/asynciterable/as.ts b/src/add/asynciterable/as.ts deleted file mode 100644 index 195d8601..00000000 --- a/src/add/asynciterable/as.ts +++ /dev/null @@ -1,12 +0,0 @@ -import { AsyncIterableX } from '../../asynciterable/asynciterablex'; -import { as as asStatic } from '../../asynciterable/as'; - -/** @nocollapse */ -AsyncIterableX.as = asStatic; - -declare module '../../asynciterable/asynciterablex' { - // eslint-disable-next-line no-shadow - namespace AsyncIterableX { - export let as: typeof asStatic; - } -} diff --git a/src/add/asynciterable/from.ts b/src/add/asynciterable/from.ts deleted file mode 100644 index 698e43c2..00000000 --- a/src/add/asynciterable/from.ts +++ /dev/null @@ -1,16 +0,0 @@ -import { AsyncIterableX } from '../../asynciterable/asynciterablex'; -import { from as fromStatic } from '../../asynciterable/from'; - -/** @nocollapse */ -AsyncIterableX.from = fromStatic; - -export declare namespace asynciterable { - let from: typeof fromStatic; -} - -declare module '../../asynciterable/asynciterablex' { - // eslint-disable-next-line no-shadow - namespace AsyncIterableX { - export { fromStatic as from }; - } -} diff --git a/src/add/iterable/as.ts b/src/add/iterable/as.ts deleted file mode 100644 index 47e52cf2..00000000 --- a/src/add/iterable/as.ts +++ /dev/null @@ -1,12 +0,0 @@ -import { IterableX } from '../../iterable/iterablex'; -import { as as asStatic } from '../../iterable/as'; - -/** @nocollapse */ -IterableX.as = asStatic; - -declare module '../../iterable/iterablex' { - // eslint-disable-next-line no-shadow - namespace IterableX { - export let as: typeof asStatic; - } -} diff --git a/src/add/iterable/from.ts b/src/add/iterable/from.ts deleted file mode 100644 index 32494176..00000000 --- a/src/add/iterable/from.ts +++ /dev/null @@ -1,16 +0,0 @@ -import { IterableX } from '../../iterable/iterablex'; -import { from as fromStatic } from '../../iterable/from'; - -/** @nocollapse */ -IterableX.from = fromStatic; - -export declare namespace iterable { - let from: typeof fromStatic; -} - -declare module '../../iterable/iterablex' { - // eslint-disable-next-line no-shadow - namespace IterableX { - export { fromStatic as from }; - } -} diff --git a/src/asynciterable/as.ts b/src/asynciterable/as.ts deleted file mode 100644 index 8f0e1f4d..00000000 --- a/src/asynciterable/as.ts +++ /dev/null @@ -1,67 +0,0 @@ -import { AsyncIterableInput, AsyncIterableX } from './asynciterablex'; -import { - isIterable, - isAsyncIterable, - isArrayLike, - isObservable, - isPromise, -} from '../util/isiterable'; -import { identityAsync } from '../util/identity'; -import { - FromObservableAsyncIterable, - FromPromiseIterable, - FromAsyncIterable, - FromArrayIterable, -} from './from'; - -/** - * Converts an existing string into an async-iterable of characters. - * - * @param {string} source The string to convert to an async-iterable. - * @returns {AsyncIterableX} An async-iterable stream of characters from the source. - */ -export function as(source: string): AsyncIterableX; -/** - * Converts the async iterable like input into an async-iterable. - * - * @template T The type of elements in the async-iterable like sequence. - * @param {AsyncIterableInput} source The async-iterable like input to convert to an async-iterable. - * @returns {AsyncIterableX} An async-iterable stream from elements in the async-iterable like sequence. - */ -export function as(source: AsyncIterableInput): AsyncIterableX; -/** - * Converts the single element into an async-iterable sequence. - * - * @template T The type of the input to turn into an async-iterable sequence. - * @param {T} source The single element to turn into an async-iterable sequence. - * @returns {AsyncIterableX} An async-iterable sequence which contains the single element. - */ -export function as(source: T): AsyncIterableX; -/** - * Converts the input into an async-iterable sequence. - * - * @param {*} source The source to convert to an async-iterable sequence. - * @returns {AsyncIterableX<*>} An async-iterable containing the input. - */ -/** @nocollapse */ -export function as(source: any): AsyncIterableX { - if (source instanceof AsyncIterableX) { - return source; - } - if (typeof source === 'string') { - return new FromArrayIterable([source], identityAsync); - } - if (isIterable(source) || isAsyncIterable(source)) { - return new FromAsyncIterable(source, identityAsync); - } - if (isPromise(source)) { - return new FromPromiseIterable(source, identityAsync); - } - if (isObservable(source)) { - return new FromObservableAsyncIterable(source, identityAsync); - } - if (isArrayLike(source)) { - return new FromArrayIterable(source, identityAsync); - } - return new FromArrayIterable([source], identityAsync); -} diff --git a/src/asynciterable/asynciterablex.ts b/src/asynciterable/asynciterablex.ts index 054a2e18..583a4ba3 100644 --- a/src/asynciterable/asynciterablex.ts +++ b/src/asynciterable/asynciterablex.ts @@ -1,23 +1,19 @@ -import { as as asAsyncIterable } from './as'; -import { _initialize as _initializeFrom } from './from'; import { OperatorAsyncFunction, UnaryFunction } from '../interfaces'; import { Observable } from '../observer'; -import { isReadableNodeStream, isWritableNodeStream } from '../util/isiterable'; - -class WithAbortAsyncIterable implements AsyncIterable { - private _source: AsyncIterable; - private _signal: AbortSignal; - - constructor(source: AsyncIterable, signal: AbortSignal) { - this._source = source; - this._signal = signal; - } - - [Symbol.asyncIterator](): AsyncIterator { - // @ts-ignore - return this._source[Symbol.asyncIterator](this._signal); - } -} +import { bindCallback } from '../util/bindcallback'; +import { identityAsync } from '../util/identity'; +import { + isReadableNodeStream, + isWritableNodeStream, + isIterable, + isAsyncIterable, + isArrayLike, + isIterator, + isPromise, + isObservable, +} from '../util/isiterable'; +import { toLength } from '../util/tolength'; +import { AbortError, throwIfAborted } from '../aborterror'; /** * This class serves as the base for all operations which support [Symbol.asyncIterator]. @@ -25,6 +21,7 @@ class WithAbortAsyncIterable implements AsyncIterable { export abstract class AsyncIterableX implements AsyncIterable { abstract [Symbol.asyncIterator](signal?: AbortSignal): AsyncIterator; + /** @nocollapse */ async forEach( projection: (value: T, index: number, signal?: AbortSignal) => void | Promise, thisArg?: any, @@ -47,10 +44,87 @@ export abstract class AsyncIterableX implements AsyncIterable { const n = args.length; let acc: any = this; while (++i < n) { - acc = args[i](asAsyncIterable(acc)); + acc = args[i](AsyncIterableX.as(acc)); } return acc; } + + /** @nocollapse */ + static from( + source: AsyncIterableInput, + selector: (value: TSource, index: number) => TResult | Promise = identityAsync, + thisArg?: any + ): AsyncIterableX { + const fn = bindCallback(selector, thisArg, 2); + if (isIterable(source) || isAsyncIterable(source)) { + return new FromAsyncIterable(source, fn); + } + if (isPromise(source)) { + return new FromPromiseIterable(source, fn); + } + if (isObservable(source)) { + return new FromObservableAsyncIterable(source, fn); + } + if (isArrayLike(source)) { + return new FromArrayIterable(source, fn); + } + if (isIterator(source)) { + return new FromAsyncIterable({ [Symbol.asyncIterator]: () => source }, fn); + } + throw new TypeError('Input type not supported'); + } + + /** + * Converts an existing string into an async-iterable of characters. + * + * @param {string} source The string to convert to an async-iterable. + * @returns {AsyncIterableX} An async-iterable stream of characters from the source. + */ + static as(source: string): AsyncIterableX; + /** + * Converts the async iterable like input into an async-iterable. + * + * @template T The type of elements in the async-iterable like sequence. + * @param {AsyncIterableInput} source The async-iterable like input to convert to an async-iterable. + * @returns {AsyncIterableX} An async-iterable stream from elements in the async-iterable like sequence. + */ + static as(source: AsyncIterableInput): AsyncIterableX; + /** + * Converts the single element into an async-iterable sequence. + * + * @template T The type of the input to turn into an async-iterable sequence. + * @param {T} source The single element to turn into an async-iterable sequence. + * @returns {AsyncIterableX} An async-iterable sequence which contains the single element. + */ + static as(source: T): AsyncIterableX; + /** + * Converts the input into an async-iterable sequence. + * + * @param {*} source The source to convert to an async-iterable sequence. + * @returns {AsyncIterableX<*>} An async-iterable containing the input. + */ + /** @nocollapse */ + static as(source: any): AsyncIterableX { + if (source instanceof AsyncIterableX) { + return source; + } + if (typeof source === 'string') { + return new FromArrayIterable([source], identityAsync); + } + if (isIterable(source) || isAsyncIterable(source)) { + return new FromAsyncIterable(source, identityAsync); + } + if (isPromise(source)) { + return new FromPromiseIterable(source, identityAsync); + } + if (isObservable(source)) { + return new FromObservableAsyncIterable(source, identityAsync); + } + if (isArrayLike(source)) { + return new FromArrayIterable(source, identityAsync); + } + return new FromArrayIterable([source], identityAsync); + } } (AsyncIterableX.prototype)[Symbol.toStringTag] = 'AsyncIterableX'; @@ -63,7 +137,218 @@ Object.defineProperty(AsyncIterableX, Symbol.hasInstance, { }, }); -_initializeFrom(AsyncIterableX); +const ARRAY_VALUE = 'value'; +const ARRAY_ERROR = 'error'; + +interface AsyncSinkItem { + type: string; + value?: T; + error?: any; +} + +interface AsyncResolver { + resolve: (value: T | PromiseLike) => void; + reject: (reason?: any) => void; +} + +export class AsyncSink implements AsyncIterableIterator { + private _ended: boolean; + private _values: AsyncSinkItem[]; + private _resolvers: AsyncResolver>[]; + + constructor() { + this._ended = false; + this._values = []; + this._resolvers = []; + } + + [Symbol.asyncIterator]() { + return this; + } + + write(value: TSource) { + this._push({ type: ARRAY_VALUE, value }); + } + + error(error: any) { + this._push({ type: ARRAY_ERROR, error }); + } + + private _push(item: AsyncSinkItem) { + if (this._ended) { + throw new Error('AsyncSink already ended'); + } + + if (this._resolvers.length > 0) { + const { resolve, reject } = this._resolvers.shift()!; + if (item.type === ARRAY_ERROR) { + reject(item.error!); + } else { + resolve({ done: false, value: item.value! }); + } + } else { + this._values.push(item); + } + } + + next() { + if (this._values.length > 0) { + const { type, value, error } = this._values.shift()!; + if (type === ARRAY_ERROR) { + return Promise.reject(error); + } else { + return Promise.resolve({ done: false, value } as IteratorResult); + } + } + + if (this._ended) { + return Promise.resolve({ done: true } as IteratorResult); + } + + return new Promise>((resolve, reject) => { + this._resolvers.push({ resolve, reject }); + }); + } + + end() { + while (this._resolvers.length > 0) { + this._resolvers.shift()!.resolve({ done: true } as IteratorResult); + } + this._ended = true; + } +} + +export class FromArrayIterable extends AsyncIterableX { + private _source: ArrayLike; + private _selector: (value: TSource, index: number) => TResult | Promise; + + constructor( + source: ArrayLike, + selector: (value: TSource, index: number) => TResult | Promise + ) { + super(); + this._source = source; + this._selector = selector; + } + + async *[Symbol.asyncIterator]() { + let i = 0; + const length = toLength((>this._source).length); + while (i < length) { + yield await this._selector(this._source[i], i++); + } + } +} + +export class FromAsyncIterable extends AsyncIterableX { + private _source: Iterable> | AsyncIterable; + private _selector: (value: TSource, index: number) => TResult | Promise; + + constructor( + source: Iterable> | AsyncIterable, + selector: (value: TSource, index: number) => TResult | Promise + ) { + super(); + this._source = source; + this._selector = selector; + } + + async *[Symbol.asyncIterator]() { + let i = 0; + for await (const item of >this._source) { + yield await this._selector(item, i++); + } + } +} + +export class FromPromiseIterable extends AsyncIterableX { + private _source: PromiseLike; + private _selector: (value: TSource, index: number) => TResult | Promise; + + constructor( + source: PromiseLike, + selector: (value: TSource, index: number) => TResult | Promise + ) { + super(); + this._source = source; + this._selector = selector; + } + + async *[Symbol.asyncIterator]() { + const item = await this._source; + yield await this._selector(item, 0); + } +} + +export class FromObservableAsyncIterable extends AsyncIterableX< + TResult +> { + private _observable: Observable; + private _selector: (value: TSource, index: number) => TResult | Promise; + + constructor( + observable: Observable, + selector: (value: TSource, index: number) => TResult | Promise + ) { + super(); + this._observable = observable; + this._selector = selector; + } + + async *[Symbol.asyncIterator](signal?: AbortSignal) { + throwIfAborted(signal); + + const sink: AsyncSink = new AsyncSink(); + const subscription = this._observable.subscribe({ + next(value: TSource) { + sink.write(value); + }, + error(err: any) { + sink.error(err); + }, + complete() { + sink.end(); + }, + }); + + function onAbort() { + sink.error(new AbortError()); + } + + if (signal) { + signal.addEventListener('abort', onAbort); + } + + let i = 0; + try { + for (let next; !(next = await sink.next()).done; ) { + throwIfAborted(signal); + yield await this._selector(next.value!, i++); + } + } finally { + if (signal) { + signal.removeEventListener('abort', onAbort); + } + + subscription.unsubscribe(); + } + } +} + +class WithAbortAsyncIterable implements AsyncIterable { + private _source: AsyncIterable; + private _signal: AbortSignal; + + constructor(source: AsyncIterable, signal: AbortSignal) { + this._source = source; + this._signal = signal; + } + + [Symbol.asyncIterator](): AsyncIterator { + // @ts-ignore + return this._source[Symbol.asyncIterator](this._signal); + } +} export type AsyncIterableInput = | AsyncIterable @@ -165,12 +450,12 @@ try { while (++i < n) { next = args[i]; if (typeof next === 'function') { - prev = next(asAsyncIterable(prev)); + prev = next(AsyncIterableX.as(prev)); } else if (isWritableNodeStream(next)) { ({ end = true } = args[i + 1] || {}); // prettier-ignore - return isReadableNodeStream(prev) ? prev.pipe(next, {end}) : - asAsyncIterable(prev).toNodeStream(readableOpts(next)).pipe(next, {end}); + return isReadableNodeStream(prev) ? prev.pipe(next, { end }) : + AsyncIterableX.as(prev).toNodeStream(readableOpts(next)).pipe(next, { end }); } } return prev; diff --git a/src/asynciterable/from.ts b/src/asynciterable/from.ts deleted file mode 100644 index d9f51f83..00000000 --- a/src/asynciterable/from.ts +++ /dev/null @@ -1,192 +0,0 @@ -import { AsyncIterableInput, AsyncIterableX } from './asynciterablex'; -import { identityAsync } from '../util/identity'; -import { bindCallback } from '../util/bindcallback'; -import { - isIterable, - isAsyncIterable, - isArrayLike, - isIterator, - isPromise, - isObservable, -} from '../util/isiterable'; -import { Observable } from '../observer'; -import { toLength } from '../util/tolength'; -import { AsyncSink } from './asyncsink'; -import { AbortError, throwIfAborted } from '../aborterror'; - -export let from: ( - source: AsyncIterableInput, - selector?: (value: TSource, index: number) => TResult | Promise, - thisArg?: any -) => AsyncIterableX; - -export let FromArrayIterable: new ( - source: ArrayLike, - selector: (value: TSource, index: number) => TResult | Promise -) => AsyncIterableX; - -export let FromAsyncIterable: new ( - source: Iterable> | AsyncIterable, - selector: (value: TSource, index: number) => TResult | Promise -) => AsyncIterableX; - -export let FromPromiseIterable: new ( - source: PromiseLike, - selector: (value: TSource, index: number) => TResult | Promise -) => AsyncIterableX; - -export let FromObservableAsyncIterable: new ( - observable: Observable, - selector: (value: TSource, index: number) => TResult | Promise -) => AsyncIterableX; - -export function _initialize(Ctor: typeof AsyncIterableX) { - /** @nocollapse */ - from = function ( - source: AsyncIterableInput, - selector: (value: TSource, index: number) => TResult | Promise = identityAsync, - thisArg?: any - ): AsyncIterableX { - const fn = bindCallback(selector, thisArg, 2); - if (isIterable(source) || isAsyncIterable(source)) { - return new FromAsyncIterable(source, fn); - } - if (isPromise(source)) { - return new FromPromiseIterable(source, fn); - } - if (isObservable(source)) { - return new FromObservableAsyncIterable(source, fn); - } - if (isArrayLike(source)) { - return new FromArrayIterable(source, fn); - } - if (isIterator(source)) { - return new FromAsyncIterable({ [Symbol.asyncIterator]: () => source }, fn); - } - throw new TypeError('Input type not supported'); - }; - - // eslint-disable-next-line no-shadow - FromArrayIterable = class FromArrayIterable extends Ctor { - private _source: ArrayLike; - private _selector: (value: TSource, index: number) => TResult | Promise; - - constructor( - source: ArrayLike, - selector: (value: TSource, index: number) => TResult | Promise - ) { - super(); - this._source = source; - this._selector = selector; - } - - async *[Symbol.asyncIterator]() { - let i = 0; - const length = toLength((>this._source).length); - while (i < length) { - yield await this._selector(this._source[i], i++); - } - } - }; - - // eslint-disable-next-line no-shadow - FromAsyncIterable = class FromAsyncIterable extends Ctor { - private _source: Iterable> | AsyncIterable; - private _selector: (value: TSource, index: number) => TResult | Promise; - - constructor( - source: Iterable> | AsyncIterable, - selector: (value: TSource, index: number) => TResult | Promise - ) { - super(); - this._source = source; - this._selector = selector; - } - - async *[Symbol.asyncIterator]() { - let i = 0; - for await (const item of >this._source) { - yield await this._selector(item, i++); - } - } - }; - - // eslint-disable-next-line no-shadow - FromPromiseIterable = class FromPromiseIterable extends Ctor< - TResult - > { - private _source: PromiseLike; - private _selector: (value: TSource, index: number) => TResult | Promise; - - constructor( - source: PromiseLike, - selector: (value: TSource, index: number) => TResult | Promise - ) { - super(); - this._source = source; - this._selector = selector; - } - - async *[Symbol.asyncIterator]() { - const item = await this._source; - yield await this._selector(item, 0); - } - }; - - // eslint-disable-next-line no-shadow - FromObservableAsyncIterable = class FromObservableAsyncIterable< - TSource, - TResult = TSource - > extends Ctor { - private _observable: Observable; - private _selector: (value: TSource, index: number) => TResult | Promise; - - constructor( - observable: Observable, - selector: (value: TSource, index: number) => TResult | Promise - ) { - super(); - this._observable = observable; - this._selector = selector; - } - - async *[Symbol.asyncIterator](signal?: AbortSignal) { - throwIfAborted(signal); - - const sink: AsyncSink = new AsyncSink(); - const subscription = this._observable.subscribe({ - next(value: TSource) { - sink.write(value); - }, - error(err: any) { - sink.error(err); - }, - complete() { - sink.end(); - }, - }); - - function onAbort() { - sink.error(new AbortError()); - } - - if (signal) { - signal.addEventListener('abort', onAbort); - } - - let i = 0; - try { - for (let next; !(next = await sink.next()).done; ) { - throwIfAborted(signal); - yield await this._selector(next.value!, i++); - } - } finally { - if (signal) { - signal.removeEventListener('abort', onAbort); - } - - subscription.unsubscribe(); - } - } - }; -} diff --git a/src/asynciterable/fromevent.ts b/src/asynciterable/fromevent.ts index def334da..2d701ea9 100644 --- a/src/asynciterable/fromevent.ts +++ b/src/asynciterable/fromevent.ts @@ -1,9 +1,17 @@ import { AsyncIterableX } from './asynciterablex'; import { fromEventPattern } from './fromeventpattern'; +import { isFunction } from '../util/isiterable'; + +type CommonEventHandler = (...args: any[]) => void; + +export interface OnOffEventEmitter { + on(event: string | symbol, listener: CommonEventHandler): this; + off(event: string | symbol, listener: CommonEventHandler): this; +} export interface NodeEventEmitter { - addListener(event: string | symbol, listener: (...args: any[]) => void): this; - removeListener(event: string | symbol, listener: (...args: any[]) => void): this; + addListener(event: string | symbol, listener: CommonEventHandler): this; + removeListener(event: string | symbol, listener: CommonEventHandler): this; } export type EventListenerOptions = @@ -14,20 +22,38 @@ export type EventListenerOptions = } | boolean; -export type EventedTarget = EventTarget | NodeEventEmitter; +export type EventedTarget = EventTarget | OnOffEventEmitter | NodeEventEmitter; + +function isMessagePortEventEmitter(obj: any): obj is OnOffEventEmitter { + return !!obj && isFunction(obj.on) && isFunction(obj.off); +} function isNodeEventEmitter(obj: any): obj is NodeEventEmitter { - return !!obj && typeof obj.addListener === 'function' && typeof obj.removeListener === 'function'; + return !!obj && isFunction(obj.addListener) && isFunction(obj.removeListener); } function isEventTarget(obj: any): obj is EventTarget { - return ( - !!obj && - typeof obj.addEventListener === 'function' && - typeof obj.removeEventListener === 'function' - ); + return !!obj && isFunction(obj.addEventListener) && isFunction(obj.removeEventListener); } +export function fromEvent(obj: EventedTarget, eventName: string): AsyncIterableX; +export function fromEvent( + obj: EventedTarget, + eventName: string, + resultSelector: (...args: any[]) => TSource +): AsyncIterableX; +export function fromEvent( + obj: EventedTarget, + eventName: string, + options: EventListenerOptions +): AsyncIterableX; +export function fromEvent( + obj: EventedTarget, + eventName: string, + options: EventListenerOptions, + resultSelector: (...args: any[]) => TSource +): AsyncIterableX; + /** * Converts an event emitter event into an async-iterable stream. * @@ -35,24 +61,40 @@ function isEventTarget(obj: any): obj is EventTarget { * @param {EventedTarget} obj The object that emits the events to turn into an async-iterable. * @param {string} type The name of the event to listen for creation of the async-iterable. * @param {EventListenerOptions} [options] The options for listening to the events such as capture, passive and once. + * @param {(...args: any[]) => TSource} [resultSelector] The result selector for the event. * @returns {AsyncIterableX} An async-iterable sequence created from the events emitted from the evented target. */ export function fromEvent( obj: EventedTarget, type: string, - options?: EventListenerOptions + options?: EventListenerOptions | ((...args: any[]) => TSource), + resultSelector?: (...args: any[]) => TSource ): AsyncIterableX { + if (isFunction(options)) { + resultSelector = options; + options = undefined; + } + if (isEventTarget(obj)) { const target = obj; return fromEventPattern( - (h) => target.addEventListener(type, h, options), - (h) => target.removeEventListener(type, h, options) + (h) => target.addEventListener(type, h, options as EventListenerOptions), + (h) => target.removeEventListener(type, h, options as EventListenerOptions), + resultSelector + ); + } else if (isMessagePortEventEmitter(obj)) { + const target = obj; + return fromEventPattern( + (h) => target.on(type, h), + (h) => target.off(type, h), + resultSelector ); } else if (isNodeEventEmitter(obj)) { const target = obj; return fromEventPattern( (h) => target.addListener(type, h), - (h) => target.removeListener(type, h) + (h) => target.removeListener(type, h), + resultSelector ); } else { throw new TypeError('Unsupported event target'); diff --git a/src/asynciterable/fromeventpattern.ts b/src/asynciterable/fromeventpattern.ts index 97e9d27d..43d41287 100644 --- a/src/asynciterable/fromeventpattern.ts +++ b/src/asynciterable/fromeventpattern.ts @@ -1,9 +1,17 @@ +import { memoize } from './operators/memoize'; +import { identity } from '../util/identity'; +import { isFunction } from '../util/isiterable'; import { AsyncIterableX } from './asynciterablex'; import { AsyncSink } from './asyncsink'; -import { memoize } from './operators/memoize'; + +const { isArray } = Array; + +function callOrApply(fn: (...values: T[]) => R, args: T | T[]): R { + return isArray(args) ? fn(...args) : fn(args); +} /** - * Creates asnyc-iterable from an event emitter by adding handlers for both listening and unsubscribing from events. + * Creates async-iterable from an event emitter by adding handlers for both listening and unsubscribing from events. * * @template TSource The type of elements in the event emitter. * @param {(handler: (...args: any[]) => void) => void} addHandler The function to add a listener to the source. @@ -12,20 +20,28 @@ import { memoize } from './operators/memoize'; */ export function fromEventPattern( addHandler: (handler: (...args: any[]) => void) => void, - removeHandler: (handler: (...args: any[]) => void) => void + removeHandler: (handler: (...args: any[]) => void) => void, + resultSelector?: (...args: any[]) => TSource ): AsyncIterableX { + if (!isFunction(resultSelector)) { + resultSelector = identity; + } + const sink = new AsyncSink(); - const handler = (e: TSource) => sink.write(e); + const handler = (...args: any[]) => sink.write(callOrApply(resultSelector!, args)); addHandler(handler); - const yielder = async function* () { - for (let next; !(next = await sink.next()).done; ) { - yield next.value; + const loop = async function* () { + try { + for (let next; !(next = await sink.next()).done; ) { + yield next.value; + } + } finally { + removeHandler(handler); + sink.end(); } - removeHandler(handler); - sink.end(); }; - return memoize()(yielder()); + return memoize()(loop()); } diff --git a/src/asynciterable/index.ts b/src/asynciterable/index.ts index 9052cf65..c1894543 100644 --- a/src/asynciterable/index.ts +++ b/src/asynciterable/index.ts @@ -1,8 +1,6 @@ -export * from './as'; export * from './asyncifyerrback'; export * from './asyncify'; export * from './asynciterablex'; -export * from './asyncsink'; export * from './average'; export * from './catcherror'; export * from './combinelatest'; @@ -20,7 +18,6 @@ export * from './forkjoin'; export * from './fromdomstream'; export * from './fromeventpattern'; export * from './fromevent'; -export * from './from'; export * from './generate'; export * from './generatetime'; export * from './iif'; @@ -36,7 +33,6 @@ export * from './minby'; export * from './never'; export * from './of'; export * from './onerrorresumenext'; -export * from './pipe'; export * from './race'; export * from './range'; export * from './reduceright'; @@ -54,3 +50,7 @@ export * from './toobservable'; export * from './toset'; export * from './whiledo'; export * from './zip'; + +import { AsyncIterableX } from './asynciterablex'; +export const as = AsyncIterableX.as; +export const from = AsyncIterableX.from; diff --git a/src/asynciterable/operators/_flatten.ts b/src/asynciterable/operators/_flatten.ts index 9293b364..df2127a9 100644 --- a/src/asynciterable/operators/_flatten.ts +++ b/src/asynciterable/operators/_flatten.ts @@ -3,7 +3,6 @@ import { wrapWithAbort } from '../operators/withabort'; import { AbortError, throwIfAborted } from '../../aborterror'; import { safeRace } from '../../util/safeRace'; import { isPromise } from '../../util/isiterable'; -import { as as asAsyncIterable } from '../as'; export type FlattenConcurrentSelector = ( value: TSource, @@ -157,7 +156,7 @@ export class FlattenConcurrentAsyncIterable extends AsyncItera const wrapAndPullInner = (inner: AsyncIterableInput | TResult) => { inners[index - 1] = wrapIterator( - asAsyncIterable(inner), + AsyncIterableX.as(inner), index, Type.INNER, innerSignal diff --git a/src/asynciterable/operators/groupjoin.ts b/src/asynciterable/operators/groupjoin.ts index 5bbfd285..d239cbd6 100644 --- a/src/asynciterable/operators/groupjoin.ts +++ b/src/asynciterable/operators/groupjoin.ts @@ -1,7 +1,6 @@ import { AsyncIterableX } from '../asynciterablex'; import { createGrouping } from './_grouping'; import { empty } from '../empty'; -import { from } from '../from'; import { identity } from '../../util/identity'; import { OperatorAsyncFunction } from '../../interfaces'; import { wrapWithAbort } from './withabort'; @@ -43,7 +42,7 @@ export class GroupJoinAsyncIterable extends Async for await (const outerElement of wrapWithAbort(this._outer, signal)) { const outerKey = await this._outerSelector(outerElement, signal); const innerElements = map.has(outerKey) ? >map.get(outerKey) : empty(); - yield await this._resultSelector(outerElement, from(innerElements), signal); + yield await this._resultSelector(outerElement, AsyncIterableX.as(innerElements), signal); } } } diff --git a/src/asynciterable/operators/mergeall.ts b/src/asynciterable/operators/mergeall.ts index 22f0fc27..0b8c69a6 100644 --- a/src/asynciterable/operators/mergeall.ts +++ b/src/asynciterable/operators/mergeall.ts @@ -1,4 +1,4 @@ -import { as } from '../as'; +import { AsyncIterableX } from '../asynciterablex'; import { flatMap } from './flatmap'; /** @@ -9,6 +9,6 @@ import { flatMap } from './flatmap'; */ export function mergeAll(concurrent = Infinity) { return function mergeAllOperatorFunction(source: AsyncIterable>) { - return as(source)['pipe'](flatMap((s) => s, concurrent)); + return AsyncIterableX.as(source)['pipe'](flatMap((s) => s, concurrent)); }; } diff --git a/src/asynciterable/operators/startwith.ts b/src/asynciterable/operators/startwith.ts index 5d6a5491..d9cceeca 100644 --- a/src/asynciterable/operators/startwith.ts +++ b/src/asynciterable/operators/startwith.ts @@ -1,5 +1,4 @@ import { AsyncIterableX } from '../asynciterablex'; -import { MonoTypeOperatorAsyncFunction } from '../../interfaces'; import { wrapWithAbort } from './withabort'; import { throwIfAborted } from '../../aborterror'; @@ -29,12 +28,12 @@ export class StartWithAsyncIterable extends AsyncIterableX { * * @template TSource The type of the elements in the source sequence. * @param {...TSource[]} args Elements to prepend to the specified sequence. - * @returns {MonoTypeOperatorAsyncFunction} The source sequence prepended with the specified values. + * @returns The source sequence prepended with the specified values. */ -export function startWith(...args: TSource[]): MonoTypeOperatorAsyncFunction { - return function startWithOperatorFunction( - source: AsyncIterable - ): AsyncIterableX { - return new StartWithAsyncIterable(source, args); +export function startWith(...args: TSource) { + return function startWithOperatorFunction( + source: AsyncIterable + ): AsyncIterableX { + return new StartWithAsyncIterable(source, args); }; } diff --git a/src/asynciterable/operators/switchmap.ts b/src/asynciterable/operators/switchmap.ts index babd3dd0..0c04be80 100644 --- a/src/asynciterable/operators/switchmap.ts +++ b/src/asynciterable/operators/switchmap.ts @@ -16,7 +16,7 @@ import { OperatorAsyncFunction } from '../../interfaces'; * @returns {OperatorAsyncFunction} An operator that creates an async-iterable sequence whose * elements are the result of invoking the one-to-many transform function on each element of the input sequence. */ -export function switchMap( +export function switchMap( selector: FlattenConcurrentSelector, thisArg?: any ): OperatorAsyncFunction { diff --git a/src/asynciterable/pipe.ts b/src/asynciterable/pipe.ts deleted file mode 100644 index 7eb309c1..00000000 --- a/src/asynciterable/pipe.ts +++ /dev/null @@ -1,95 +0,0 @@ -import { OperatorAsyncFunction } from '../interfaces'; -import { AsyncIterableX } from './asynciterablex'; -import { from } from './from'; - -export function pipe(source: AsyncIterable): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction, - op3: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction, - op3: OperatorAsyncFunction, - op4: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction, - op3: OperatorAsyncFunction, - op4: OperatorAsyncFunction, - op5: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction, - op3: OperatorAsyncFunction, - op4: OperatorAsyncFunction, - op5: OperatorAsyncFunction, - op6: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction, - op3: OperatorAsyncFunction, - op4: OperatorAsyncFunction, - op5: OperatorAsyncFunction, - op6: OperatorAsyncFunction, - op7: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction, - op3: OperatorAsyncFunction, - op4: OperatorAsyncFunction, - op5: OperatorAsyncFunction, - op6: OperatorAsyncFunction, - op7: OperatorAsyncFunction, - op8: OperatorAsyncFunction -): AsyncIterableX; -export function pipe( - source: AsyncIterable, - op1: OperatorAsyncFunction, - op2: OperatorAsyncFunction, - op3: OperatorAsyncFunction, - op4: OperatorAsyncFunction, - op5: OperatorAsyncFunction, - op6: OperatorAsyncFunction, - op7: OperatorAsyncFunction, - op8: OperatorAsyncFunction, - op9: OperatorAsyncFunction -): AsyncIterableX; - -export function pipe( - source: AsyncIterable, - ...operations: OperatorAsyncFunction[] -): AsyncIterableX { - if (operations.length === 0) { - return source instanceof AsyncIterableX ? source : from(source); - } - - const piped = (input: AsyncIterable): AsyncIterableX => { - return operations.reduce( - (prev: any, fn: OperatorAsyncFunction) => fn(prev), - input as any - ); - }; - - return piped(source); -} diff --git a/src/asynciterable/toobservable.ts b/src/asynciterable/toobservable.ts index 2a6a9aaa..7054c2ef 100644 --- a/src/asynciterable/toobservable.ts +++ b/src/asynciterable/toobservable.ts @@ -18,9 +18,12 @@ class AsyncIterableObservable implements Observable { this._source = source; } + /** @nocollapse */ [symbolObservable](): Observable { return this; } + + /** @nocollapse */ subscribe( next?: PartialObserver | ((value: TSource) => any) | null, error?: ((err: any) => any) | null, diff --git a/src/iterable/as.ts b/src/iterable/as.ts deleted file mode 100644 index 081d1cf8..00000000 --- a/src/iterable/as.ts +++ /dev/null @@ -1,52 +0,0 @@ -import { IterableX } from './iterablex'; -import { FromIterable } from './from'; -import { isIterable, isArrayLike } from '../util/isiterable'; -import { identity } from '../util/identity'; - -/** - * Converts an existing string into an iterable of characters. - * - * @param {string} source The string to convert to an iterable. - * @returns {IterableX} An terable stream of characters from the source. - */ -export function as(source: string): IterableX; -/** - * Converts the iterable like input into an iterable. - * - * @template T The tyep of elements in the source iterable. - * @param {Iterable} source The iterable to convert to an iterable. - * @returns {IterableX} An iterable stream of the source sequence. - */ -export function as(source: Iterable): IterableX; -/** - * Converts an array-like object to an iterable. - * - * @template T The type of elements in the source array-like sequence. - * @param {ArrayLike} source The array-like sequence to convert to an iterable. - * @returns {IterableX} The iterable containing the elements from the array-like sequence. - */ -export function as(source: ArrayLike): IterableX; -/** - * Converts the object into a singleton in an iterable sequence. - * - * @template T The type of element to turn into an iterable sequence. - * @param {T} source The item to turn into an iterable sequence. - * @returns {IterableX} An iterable sequence from the source object. - */ -export function as(source: T): IterableX; -/** @nocollapse */ -export function as(source: any) { - if (source instanceof IterableX) { - return source; - } - if (typeof source === 'string') { - return new FromIterable([source], identity); - } - if (isIterable(source)) { - return new FromIterable(source, identity); - } - if (isArrayLike(source)) { - return new FromIterable(source, identity); - } - return new FromIterable([source], identity); -} diff --git a/src/iterable/from.ts b/src/iterable/from.ts deleted file mode 100644 index 338f647f..00000000 --- a/src/iterable/from.ts +++ /dev/null @@ -1,70 +0,0 @@ -import { IterableX } from './iterablex'; -import { identity } from '../util/identity'; -import { bindCallback } from '../util/bindcallback'; -import { isIterable, isArrayLike, isIterator } from '../util/isiterable'; -import { toLength } from '../util/tolength'; - -/** @nocollapse */ -export let from: ( - source: Iterable | Iterator | ArrayLike, - selector?: (value: TSource, index: number) => TResult, - thisArg?: any -) => IterableX; - -/** @nocollapse */ -export let FromIterable: new ( - source: Iterable | ArrayLike, - selector: (value: TSource, index: number) => TResult -) => IterableX; - -export function _initialize(Ctor: typeof IterableX) { - /** @nocollapse */ - from = function ( - source: Iterable | Iterator | ArrayLike, - selector: (value: TSource, index: number) => TResult = identity, - thisArg?: any - ): IterableX { - const fn = bindCallback(selector, thisArg, 2); - if (isIterable(source)) { - return new FromIterable(source, fn); - } - if (isArrayLike(source)) { - return new FromIterable(source, fn); - } - if (isIterator(source)) { - return new FromIterable({ [Symbol.iterator]: () => source }, fn); - } - throw new TypeError('Input type not supported'); - }; - - // eslint-disable-next-line no-shadow - FromIterable = class FromIterable extends Ctor { - private _source: Iterable | ArrayLike; - private _fn: (value: TSource, index: number) => TResult; - - constructor( - source: Iterable | ArrayLike, - fn: (value: TSource, index: number) => TResult - ) { - super(); - this._source = source; - this._fn = fn; - } - - *[Symbol.iterator]() { - const iterable = isIterable(this._source); - let i = 0; - if (iterable) { - for (const item of >this._source) { - yield this._fn(item, i++); - } - } else { - const length = toLength((>this._source).length); - while (i < length) { - const val = (>this._source)[i]; - yield this._fn(val, i++); - } - } - } - }; -} diff --git a/src/iterable/index.ts b/src/iterable/index.ts index 3ea9b7fc..8593b1b2 100644 --- a/src/iterable/index.ts +++ b/src/iterable/index.ts @@ -1,4 +1,3 @@ -export * from './as'; export * from './average'; export * from './catcherror'; export * from './concat'; @@ -11,7 +10,6 @@ export * from './every'; export * from './findindex'; export * from './find'; export * from './first'; -export * from './from'; export * from './generate'; export * from './iif'; export * from './includes'; @@ -24,7 +22,6 @@ export * from './min'; export * from './minby'; export * from './of'; export * from './onerrorresumenext'; -export * from './pipe'; export * from './range'; export * from './reduceright'; export * from './reduce'; @@ -40,3 +37,7 @@ export * from './tomap'; export * from './toset'; export * from './whiledo'; export * from './zip'; + +import { IterableX } from './iterablex'; +export const as = IterableX.as; +export const from = IterableX.from; diff --git a/src/iterable/iterablex.ts b/src/iterable/iterablex.ts index 43c285ed..092b968a 100644 --- a/src/iterable/iterablex.ts +++ b/src/iterable/iterablex.ts @@ -1,8 +1,14 @@ -import { as as asIterable } from './as'; -import { _initialize as _initializeFrom } from './from'; +import { identity } from '../util/identity'; import { UnaryFunction, OperatorFunction } from '../interfaces'; import { bindCallback } from '../util/bindcallback'; -import { isReadableNodeStream, isWritableNodeStream } from '../util/isiterable'; +import { + isArrayLike, + isIterable, + isIterator, + isReadableNodeStream, + isWritableNodeStream, +} from '../util/isiterable'; +import { toLength } from '../util/tolength'; /** * This class serves as the base for all operations which support [Symbol.iterator]. @@ -10,6 +16,7 @@ import { isReadableNodeStream, isWritableNodeStream } from '../util/isiterable'; export abstract class IterableX implements Iterable { abstract [Symbol.iterator](): Iterator; + /** @nocollapse */ forEach(projection: (value: T, index: number) => void, thisArg?: any): void { const fn = bindCallback(projection, thisArg, 2); let i = 0; @@ -27,10 +34,75 @@ export abstract class IterableX implements Iterable { const n = args.length; let acc: any = this; while (++i < n) { - acc = args[i](asIterable(acc)); + acc = args[i](IterableX.as(acc)); } return acc; } + + /** + * Converts an existing string into an iterable of characters. + * + * @param {string} source The string to convert to an iterable. + * @returns {IterableX} An terable stream of characters from the source. + */ + static as(source: string): IterableX; + /** + * Converts the iterable like input into an iterable. + * + * @template T The tyep of elements in the source iterable. + * @param {Iterable} source The iterable to convert to an iterable. + * @returns {IterableX} An iterable stream of the source sequence. + */ + static as(source: Iterable): IterableX; + /** + * Converts an array-like object to an iterable. + * + * @template T The type of elements in the source array-like sequence. + * @param {ArrayLike} source The array-like sequence to convert to an iterable. + * @returns {IterableX} The iterable containing the elements from the array-like sequence. + */ + static as(source: ArrayLike): IterableX; + /** + * Converts the object into a singleton in an iterable sequence. + * + * @template T The type of element to turn into an iterable sequence. + * @param {T} source The item to turn into an iterable sequence. + * @returns {IterableX} An iterable sequence from the source object. + */ + static as(source: T): IterableX; + /** @nocollapse */ + static as(source: any) { + if (source instanceof IterableX) { + return source; + } + if (typeof source === 'string') { + return new FromIterable([source], identity); + } + if (isIterable(source) || isArrayLike(source)) { + return new FromIterable(source, identity); + } + + return new FromIterable([source], identity); + } + + /** @nocollapse */ + static from( + source: Iterable | Iterator | ArrayLike, + selector: (value: TSource, index: number) => TResult = identity, + thisArg?: any + ): IterableX { + const fn = bindCallback(selector, thisArg, 2); + if (isIterable(source)) { + return new FromIterable(source, fn); + } + if (isArrayLike(source)) { + return new FromIterable(source, fn); + } + if (isIterator(source)) { + return new FromIterable({ [Symbol.iterator]: () => source }, fn); + } + throw new TypeError('Input type not supported'); + } } (IterableX.prototype)[Symbol.toStringTag] = 'IterableX'; @@ -43,7 +115,35 @@ Object.defineProperty(IterableX, Symbol.hasInstance, { }, }); -_initializeFrom(IterableX); +export class FromIterable extends IterableX { + private _source: Iterable | ArrayLike; + private _fn: (value: TSource, index: number) => TResult; + + constructor( + source: Iterable | ArrayLike, + fn: (value: TSource, index: number) => TResult + ) { + super(); + this._source = source; + this._fn = fn; + } + + *[Symbol.iterator]() { + const iterable = isIterable(this._source); + let i = 0; + if (iterable) { + for (const item of >this._source) { + yield this._fn(item, i++); + } + } else { + const length = toLength((>this._source).length); + while (i < length) { + const val = (>this._source)[i]; + yield this._fn(val, i++); + } + } + } +} type WritableOrOperatorFunction = | NodeJS.WritableStream @@ -134,12 +234,12 @@ try { while (++i < n) { next = args[i]; if (typeof next === 'function') { - prev = next(asIterable(prev)); + prev = next(IterableX.as(prev)); } else if (isWritableNodeStream(next)) { ({ end = true } = args[i + 1] || {}); // prettier-ignore - return isReadableNodeStream(prev) ? prev.pipe(next, {end}) : - asIterable(prev).toNodeStream(readableOpts(next)).pipe(next, {end}); + return isReadableNodeStream(prev) ? prev.pipe(next, { end }) : + IterableX.as(prev).toNodeStream(readableOpts(next)).pipe(next, { end }); } } return prev; diff --git a/src/iterable/pipe.ts b/src/iterable/pipe.ts deleted file mode 100644 index 0c29f163..00000000 --- a/src/iterable/pipe.ts +++ /dev/null @@ -1,92 +0,0 @@ -import { OperatorFunction } from '../interfaces'; -import { IterableX } from './iterablex'; -import { from } from './from'; - -export function pipe(source: Iterable): IterableX; -export function pipe(source: Iterable, op1: OperatorFunction): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction -): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction, - op3: OperatorFunction -): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction, - op3: OperatorFunction, - op4: OperatorFunction -): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction, - op3: OperatorFunction, - op4: OperatorFunction, - op5: OperatorFunction -): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction, - op3: OperatorFunction, - op4: OperatorFunction, - op5: OperatorFunction, - op6: OperatorFunction -): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction, - op3: OperatorFunction, - op4: OperatorFunction, - op5: OperatorFunction, - op6: OperatorFunction, - op7: OperatorFunction -): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction, - op3: OperatorFunction, - op4: OperatorFunction, - op5: OperatorFunction, - op6: OperatorFunction, - op7: OperatorFunction, - op8: OperatorFunction -): IterableX; -export function pipe( - source: Iterable, - op1: OperatorFunction, - op2: OperatorFunction, - op3: OperatorFunction, - op4: OperatorFunction, - op5: OperatorFunction, - op6: OperatorFunction, - op7: OperatorFunction, - op8: OperatorFunction, - op9: OperatorFunction -): IterableX; - -export function pipe( - source: Iterable, - ...operations: OperatorFunction[] -): IterableX { - if (operations.length === 0) { - return source instanceof IterableX ? source : from(source); - } - - const piped = (input: Iterable): IterableX => { - return operations.reduce( - (prev: any, fn: OperatorFunction) => fn(prev), - input as any - ); - }; - - return piped(source); -} diff --git a/src/iterable/todomstream.ts b/src/iterable/todomstream.ts index 000d24e6..459f45d6 100644 --- a/src/iterable/todomstream.ts +++ b/src/iterable/todomstream.ts @@ -1,4 +1,4 @@ -import { from } from '../asynciterable/from'; +import { AsyncIterableX } from '../asynciterable/asynciterablex'; import { publish } from './operators/publish'; import { IterableX } from '../iterable/iterablex'; import { @@ -24,9 +24,9 @@ export function toDOMStream( options?: QueuingStrategy | ReadableBYOBStreamOptions | ReadableByteStreamOptions ) { if (!options || !('type' in options) || options['type'] !== 'bytes') { - return asyncIterableToDOMStream(from(source), options); + return asyncIterableToDOMStream(AsyncIterableX.as(source), options); } - return asyncIterableToDOMStream(from(source), options); + return asyncIterableToDOMStream(AsyncIterableX.as(source), options); } IterableX.prototype.tee = function (this: IterableX) {