evnty 4.6.10 → 4.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/src/index.ts CHANGED
@@ -1,38 +1,11 @@
1
- export interface Fn<A extends unknown[], R> {
2
- (...args: A): R;
3
- }
4
-
5
- export type MaybePromise<T> = Promise<T> | PromiseLike<T> | T;
6
-
7
- export interface Callback<R = void> extends Fn<[], MaybePromise<R>> {}
8
-
9
- export interface Listener<T, R = unknown> extends Fn<[T], MaybePromise<R | void>> {}
10
-
11
- export interface FilterFunction<T> {
12
- (value: T): MaybePromise<boolean>;
13
- }
14
-
15
- export interface Predicate<T, P extends T> {
16
- (value: T): value is P;
17
- }
18
-
19
- export type Filter<T, P extends T> = Predicate<T, P> | FilterFunction<T>;
20
-
21
- export interface Mapper<T, R> {
22
- (value: T): MaybePromise<R>;
23
- }
24
-
25
- export interface AsyncGenerable<T, R> {
26
- (value: T): AsyncGenerator<R, void, unknown>;
27
- }
28
-
29
- export interface Reducer<T, R> {
30
- (result: R, value: T): MaybePromise<R>;
31
- }
1
+ import { MaybePromise, Callback, Listener, FilterFunction, Predicate, Filter, Mapper, AsyncGenerable, Reducer, Expander } from './types.js';
2
+ import { Callable } from './callable.js';
3
+ import { Sequence } from './sequence.js';
32
4
 
33
- export interface Expander<T, R> {
34
- (value: T): MaybePromise<R>;
35
- }
5
+ export * from './types.js';
6
+ export * from './callable.js';
7
+ export * from './signal.js';
8
+ export * from './sequence.js';
36
9
 
37
10
  /**
38
11
  * Removes a listener from the provided array of listeners. It searches for the listener and removes all instances of it from the array.
@@ -89,26 +62,6 @@ export const setTimeoutAsync = (timeout: number, signal?: AbortSignal): Promise<
89
62
  });
90
63
  });
91
64
 
92
- /**
93
- * @internal
94
- */
95
- export interface Callable<T extends unknown[], R> {
96
- (...args: T): R;
97
- }
98
-
99
- /**
100
- * An abstract class that extends the built-in Function class. It allows instances of the class
101
- * to be called as functions. When an instance of Callable is called as a function, it will
102
- * call the function passed to its constructor with the same arguments.
103
- * @internal
104
- */
105
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
106
- export abstract class Callable<T, R> {
107
- // eslint-disable-next-line @typescript-eslint/no-unsafe-function-type
108
- constructor(func: Function) {
109
- return Object.setPrototypeOf(func, new.target.prototype);
110
- }
111
- }
112
65
  /*
113
66
  * @internal
114
67
  */
@@ -127,160 +80,9 @@ export interface EventSource<T> extends Callable<[T], boolean>, Promise<T>, Asyn
127
80
  next(): Promise<T>;
128
81
  }
129
82
 
130
- /*
131
- * @internal
132
- */
133
- export class Signal<T> extends Callable<[T], boolean> implements Promise<T>, AsyncIterable<T> {
134
- private rx?: PromiseWithResolvers<T>;
135
-
136
- constructor(private readonly abortSignal?: AbortSignal) {
137
- super((value: T) => {
138
- if (this.rx) {
139
- this.rx.resolve(value);
140
- this.rx = undefined;
141
- return true;
142
- } else {
143
- return false;
144
- }
145
- });
146
- this.abortSignal?.addEventListener(
147
- 'abort',
148
- () => {
149
- this.rx?.reject(this.abortSignal!.reason);
150
- this.rx = undefined;
151
- },
152
- { once: true },
153
- );
154
- }
155
-
156
- get [Symbol.toStringTag](): string {
157
- return `Signal(${this.abortSignal?.aborted ? 'stopped' : 'active'})`;
158
- }
159
-
160
- get promise(): Promise<T> {
161
- return this.next();
162
- }
163
-
164
- async next() {
165
- if (this.abortSignal?.aborted) {
166
- return Promise.reject(this.abortSignal.reason);
167
- }
168
- if (!this.rx) {
169
- this.rx = Promise.withResolvers<T>();
170
- }
171
- return this.rx.promise;
172
- }
173
-
174
- catch<OK = never>(onrejected?: ((reason: any) => OK | PromiseLike<OK>) | null | undefined): Promise<T | OK> {
175
- return this.promise.catch(onrejected);
176
- }
177
-
178
- finally(onfinally?: (() => void) | null | undefined): Promise<T> {
179
- return this.promise.finally(onfinally);
180
- }
181
-
182
- then<OK = T, ERR = never>(
183
- onfulfilled?: ((value: T) => OK | PromiseLike<OK>) | null | undefined,
184
- onrejected?: ((reason: unknown) => ERR | PromiseLike<ERR>) | null | undefined,
185
- ): Promise<OK | ERR> {
186
- return this.promise.then(onfulfilled, onrejected);
187
- }
188
-
189
- [Symbol.asyncIterator](): AsyncIterator<T, void, void> {
190
- return {
191
- next: async () => {
192
- try {
193
- const value = await this;
194
- return { value, done: false };
195
- } catch {
196
- return { value: undefined, done: true };
197
- }
198
- },
199
- return: () => {
200
- return Promise.resolve({ value: undefined, done: true });
201
- },
202
- };
203
- }
204
- }
205
-
206
83
  /**
207
84
  * @internal
208
85
  */
209
- export class Sequence<T> extends Callable<[T], boolean> implements Promise<T>, AsyncIterable<T> {
210
- private sequence: T[];
211
- private nextSignal: Signal<boolean>;
212
-
213
- constructor(private readonly abortSignal?: AbortSignal) {
214
- super((value: T) => {
215
- if (this.abortSignal?.aborted) {
216
- this.nextSignal(false);
217
- return false;
218
- } else {
219
- this.sequence.push(value);
220
- if (this.sequence.length === 1) {
221
- this.nextSignal(true);
222
- }
223
- return true;
224
- }
225
- });
226
- this.sequence = [];
227
- this.nextSignal = new Signal<boolean>(this.abortSignal);
228
- this.abortSignal?.addEventListener(
229
- 'abort',
230
- () => {
231
- this.nextSignal(false);
232
- },
233
- { once: true },
234
- );
235
- }
236
-
237
- get [Symbol.toStringTag](): string {
238
- return `Sequence(${this.abortSignal?.aborted ? 'stopped' : 'active'})`;
239
- }
240
-
241
- get promise(): Promise<T> {
242
- return this.next();
243
- }
244
-
245
- async next(): Promise<T> {
246
- if (!this.sequence.length) {
247
- await this.nextSignal;
248
- }
249
- return this.sequence.shift()!;
250
- }
251
-
252
- catch<OK = never>(onrejected?: ((reason: any) => OK | PromiseLike<OK>) | null | undefined): Promise<T | OK> {
253
- return this.promise.catch(onrejected);
254
- }
255
-
256
- finally(onfinally?: (() => void) | null | undefined): Promise<T> {
257
- return this.promise.finally(onfinally);
258
- }
259
-
260
- then<OK = T, ERR = never>(
261
- onfulfilled?: ((value: T) => OK | PromiseLike<OK>) | null | undefined,
262
- onrejected?: ((reason: unknown) => ERR | PromiseLike<ERR>) | null | undefined,
263
- ): Promise<OK | ERR> {
264
- return this.promise.then(onfulfilled, onrejected);
265
- }
266
-
267
- [Symbol.asyncIterator](): AsyncIterator<T, void, void> {
268
- return {
269
- next: async () => {
270
- try {
271
- const value = await this;
272
- return { value, done: false };
273
- } catch {
274
- return { value: undefined, done: true };
275
- }
276
- },
277
- return: () => {
278
- this.nextSignal(false);
279
- return Promise.resolve({ value: undefined, done: true });
280
- },
281
- };
282
- }
283
- }
284
86
 
285
87
  /**
286
88
  * @internal
@@ -536,18 +338,26 @@ export class Event<T = unknown, R = unknown> extends Callable<[T], Promise<(void
536
338
  * ```
537
339
  */
538
340
  then<OK = T, ERR = never>(
539
- onfulfilled?: ((value: T) => OK | PromiseLike<OK>) | null | undefined,
540
- onrejected?: ((reason: unknown) => ERR | PromiseLike<ERR>) | null | undefined,
341
+ onfulfilled?: ((value: T) => OK | PromiseLike<OK>) | null,
342
+ onrejected?: ((reason: unknown) => ERR | PromiseLike<ERR>) | null,
541
343
  ): Promise<OK | ERR> {
542
- const unsubscribe: Unsubscribe[] = [];
344
+ const subscribers: Unsubscribe[] = [];
543
345
  const promise = new Promise<T>((resolve, reject) => {
544
- unsubscribe.push(this.once(resolve));
545
- unsubscribe.push(this.error.once(reject));
346
+ subscribers.push(this.once(resolve));
347
+ subscribers.push(this.error.once(reject));
546
348
  });
547
349
 
548
- return promise.then(onfulfilled, onrejected).finally(async () => {
549
- await Promise.all(unsubscribe.map((u) => u()));
550
- });
350
+ const unsubscribe = async <U>(value: U) => {
351
+ await Promise.all(subscribers.map((u) => u()));
352
+ return value;
353
+ };
354
+
355
+ return promise
356
+ .then(onfulfilled, onrejected)
357
+ .then(unsubscribe)
358
+ .catch(async (error) => {
359
+ throw await unsubscribe(error);
360
+ });
551
361
  }
552
362
 
553
363
  /**
@@ -852,7 +662,7 @@ export class Event<T = unknown, R = unknown> extends Callable<[T], Promise<(void
852
662
  orchestrate<CT, CR>(conductor: Event<CT, CR>): Event<T, R> {
853
663
  let initialized = false;
854
664
  let lastValue: T;
855
- const unsubscribe = this.on(async (event) => {
665
+ const unsubscribe = this.on((event) => {
856
666
  initialized = true;
857
667
  lastValue = event;
858
668
  });
@@ -1028,8 +838,8 @@ export class Event<T = unknown, R = unknown> extends Callable<[T], Promise<(void
1028
838
  return ctrl.signal.aborted;
1029
839
  },
1030
840
  then<TResult1 = T, TResult2 = never>(
1031
- onfulfilled?: ((value: T) => TResult1 | PromiseLike<TResult1>) | null | undefined,
1032
- onrejected?: ((reason: unknown) => TResult2 | PromiseLike<TResult2>) | null | undefined,
841
+ onfulfilled?: ((value: T) => TResult1 | PromiseLike<TResult1>) | null,
842
+ onrejected?: ((reason: unknown) => TResult2 | PromiseLike<TResult2>) | null,
1033
843
  ): Promise<TResult1 | TResult2> {
1034
844
  return pop().then(onfulfilled, onrejected);
1035
845
  },
@@ -1088,10 +898,6 @@ export const merge = <Events extends Event<any, any>[]>(...events: Events): Even
1088
898
  return mergedEvent;
1089
899
  };
1090
900
 
1091
- //export const fromIterator = (iterator: Iterator<T>): Event<T> {
1092
- //
1093
- //}
1094
-
1095
901
  /**
1096
902
  * Creates a periodic event that triggers at a specified interval. The event will automatically emit
1097
903
  * an incrementing counter value each time it triggers, starting from zero. This function is useful
@@ -1112,7 +918,9 @@ export const merge = <Events extends Event<any, any>[]>(...events: Events): Even
1112
918
  export const createInterval = <R = unknown>(interval: number): Event<number, R> => {
1113
919
  let counter = 0;
1114
920
  const intervalEvent = new Event<number, R>(() => clearInterval(timerId));
1115
- const timerId: ReturnType<typeof setInterval> = setInterval(() => intervalEvent(counter++), interval);
921
+ const timerId: ReturnType<typeof setInterval> = setInterval(() => {
922
+ void intervalEvent(counter++);
923
+ }, interval);
1116
924
  return intervalEvent;
1117
925
  };
1118
926