@dxos/async 0.8.4-main.f9ba587 → 0.8.4-main.fcc0d83b33

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.
Files changed (77) hide show
  1. package/dist/lib/browser/index.mjs +306 -269
  2. package/dist/lib/browser/index.mjs.map +4 -4
  3. package/dist/lib/browser/meta.json +1 -1
  4. package/dist/lib/node-esm/index.mjs +306 -269
  5. package/dist/lib/node-esm/index.mjs.map +4 -4
  6. package/dist/lib/node-esm/meta.json +1 -1
  7. package/dist/types/src/callback.d.ts +2 -1
  8. package/dist/types/src/callback.d.ts.map +1 -1
  9. package/dist/types/src/chain.d.ts +1 -1
  10. package/dist/types/src/chain.d.ts.map +1 -1
  11. package/dist/types/src/cleanup.d.ts +3 -3
  12. package/dist/types/src/cleanup.d.ts.map +1 -1
  13. package/dist/types/src/debounce.d.ts +37 -3
  14. package/dist/types/src/debounce.d.ts.map +1 -1
  15. package/dist/types/src/errors.d.ts.map +1 -1
  16. package/dist/types/src/event-emitter.d.ts.map +1 -1
  17. package/dist/types/src/events.d.ts.map +1 -1
  18. package/dist/types/src/index.d.ts +0 -5
  19. package/dist/types/src/index.d.ts.map +1 -1
  20. package/dist/types/src/mutex.d.ts.map +1 -1
  21. package/dist/types/src/observable-value.d.ts.map +1 -1
  22. package/dist/types/src/observable.d.ts.map +1 -1
  23. package/dist/types/src/persistent-lifecycle.d.ts +2 -2
  24. package/dist/types/src/persistent-lifecycle.d.ts.map +1 -1
  25. package/dist/types/src/stream-to-array.d.ts.map +1 -1
  26. package/dist/types/src/task-scheduling.d.ts +29 -1
  27. package/dist/types/src/task-scheduling.d.ts.map +1 -1
  28. package/dist/types/src/test-stream.d.ts.map +1 -1
  29. package/dist/types/src/testing.d.ts +13 -0
  30. package/dist/types/src/testing.d.ts.map +1 -1
  31. package/dist/types/src/timeout.d.ts +2 -2
  32. package/dist/types/src/timeout.d.ts.map +1 -1
  33. package/dist/types/src/timer.d.ts.map +1 -1
  34. package/dist/types/src/track-leaks.d.ts.map +1 -1
  35. package/dist/types/src/trigger.d.ts +11 -0
  36. package/dist/types/src/trigger.d.ts.map +1 -1
  37. package/dist/types/src/update-scheduler.d.ts.map +1 -1
  38. package/dist/types/tsconfig.tsbuildinfo +1 -1
  39. package/package.json +13 -12
  40. package/src/callback.ts +3 -3
  41. package/src/chain.ts +1 -1
  42. package/src/cleanup.ts +10 -7
  43. package/src/debounce.test.ts +69 -12
  44. package/src/debounce.ts +88 -14
  45. package/src/event-emitter.test.ts +1 -1
  46. package/src/index.ts +0 -5
  47. package/src/observable-value.test.ts +1 -1
  48. package/src/observable-value.ts +4 -2
  49. package/src/persistent-lifecycle.test.ts +1 -1
  50. package/src/persistent-lifecycle.ts +2 -2
  51. package/src/task-scheduling.ts +95 -1
  52. package/src/testing.test.ts +41 -1
  53. package/src/testing.ts +53 -0
  54. package/src/timeout.ts +27 -29
  55. package/src/trigger.ts +58 -1
  56. package/src/update-scheduler.ts +1 -1
  57. package/dist/types/src/latch.d.ts +0 -11
  58. package/dist/types/src/latch.d.ts.map +0 -1
  59. package/dist/types/src/sink.d.ts +0 -6
  60. package/dist/types/src/sink.d.ts.map +0 -1
  61. package/dist/types/src/throttle.d.ts +0 -2
  62. package/dist/types/src/throttle.d.ts.map +0 -1
  63. package/dist/types/src/throttle.test.d.ts +0 -2
  64. package/dist/types/src/throttle.test.d.ts.map +0 -1
  65. package/dist/types/src/types.d.ts +0 -2
  66. package/dist/types/src/types.d.ts.map +0 -1
  67. package/dist/types/src/until.d.ts +0 -14
  68. package/dist/types/src/until.d.ts.map +0 -1
  69. package/dist/types/src/until.test.d.ts +0 -2
  70. package/dist/types/src/until.test.d.ts.map +0 -1
  71. package/src/latch.ts +0 -60
  72. package/src/sink.ts +0 -26
  73. package/src/throttle.test.ts +0 -65
  74. package/src/throttle.ts +0 -14
  75. package/src/types.ts +0 -5
  76. package/src/until.test.ts +0 -47
  77. package/src/until.ts +0 -58
@@ -1,7 +1,7 @@
1
1
  import { createRequire } from 'node:module';const require = createRequire(import.meta.url);
2
2
 
3
3
  // src/callback.ts
4
- var createPromiseFromCallback = (run) => new Promise((resolve, reject) => {
4
+ var promiseFromCallback = (run) => new Promise((resolve, reject) => {
5
5
  run((error, value) => {
6
6
  if (error) {
7
7
  reject(error);
@@ -12,9 +12,9 @@ var createPromiseFromCallback = (run) => new Promise((resolve, reject) => {
12
12
  });
13
13
 
14
14
  // src/chain.ts
15
- var asyncChain = (chain) => async (elements) => {
15
+ var chain = (chain2) => async (elements) => {
16
16
  let result = await elements;
17
- for (const part of chain) {
17
+ for (const part of chain2) {
18
18
  result = await Promise.all(result.map(async (element) => await part(element)));
19
19
  }
20
20
  return result;
@@ -24,7 +24,7 @@ var asyncChain = (chain) => async (elements) => {
24
24
  import { ComplexMap } from "@dxos/util";
25
25
  var combine = (...cleanupFns) => {
26
26
  return () => {
27
- cleanupFns.flat().forEach((cleanupFn) => cleanupFn());
27
+ cleanupFns.flat().filter((f) => typeof f === "function").forEach((cleanupFn) => cleanupFn());
28
28
  };
29
29
  };
30
30
  var timeout = (cb, ms = 0) => {
@@ -35,16 +35,14 @@ var interval = (cb, ms) => {
35
35
  const t = setInterval(cb, ms);
36
36
  return () => clearInterval(t);
37
37
  };
38
- function addEventListener(target, type, listener, options) {
38
+ var addEventListener = (target, type, listener, options) => {
39
39
  target.addEventListener(type, listener, options);
40
40
  return () => target.removeEventListener(type, listener, options);
41
- }
41
+ };
42
42
  var SubscriptionList = class {
43
- constructor() {
44
- this._cleanups = [];
45
- }
46
- add(cb) {
47
- this._cleanups.push(cb);
43
+ _cleanups = [];
44
+ add(...cb) {
45
+ this._cleanups.push(...cb);
48
46
  return this;
49
47
  }
50
48
  clear() {
@@ -53,6 +51,7 @@ var SubscriptionList = class {
53
51
  }
54
52
  };
55
53
  var SubscriptionSet = class {
54
+ _cleanupMap;
56
55
  constructor(keyProjection) {
57
56
  this._cleanupMap = new ComplexMap(keyProjection);
58
57
  }
@@ -66,32 +65,56 @@ var SubscriptionSet = class {
66
65
  }
67
66
  };
68
67
 
69
- // src/throttle.ts
70
- var throttle = (cb, wait = 100) => {
71
- let lastCall = 0;
68
+ // src/debounce.ts
69
+ var delay = (cb, delay2 = 100) => {
70
+ let pending = false;
72
71
  return (...args) => {
73
- const now = Date.now();
74
- if (now - lastCall >= wait) {
75
- cb(...args);
76
- lastCall = now;
72
+ if (pending) {
73
+ return;
77
74
  }
75
+ pending = true;
76
+ setTimeout(() => {
77
+ try {
78
+ cb(...args);
79
+ } finally {
80
+ pending = false;
81
+ }
82
+ }, delay2);
78
83
  };
79
84
  };
80
-
81
- // src/debounce.ts
82
- var debounce = (cb, wait = 100) => {
85
+ var debounce = (cb, delay2 = 100) => {
83
86
  let t;
84
87
  return (...args) => {
85
88
  clearTimeout(t);
86
- t = setTimeout(() => cb(...args), wait);
89
+ t = setTimeout(() => cb(...args), delay2);
87
90
  };
88
91
  };
89
- var debounceAndThrottle = (cb, wait = 100) => {
90
- const debounced = debounce(cb, wait);
91
- const throttled = throttle(cb, wait);
92
+ var throttle = (cb, delay2 = 100) => {
93
+ let lastCall = 0;
92
94
  return (...args) => {
93
- debounced(...args);
94
- throttled(...args);
95
+ const now = Date.now();
96
+ if (now - lastCall >= delay2) {
97
+ cb(...args);
98
+ lastCall = now;
99
+ }
100
+ };
101
+ };
102
+ var debounceAndThrottle = (cb, delay2 = 100) => {
103
+ let timeout2;
104
+ let lastCall = 0;
105
+ return (...args) => {
106
+ const now = Date.now();
107
+ const delta = now - lastCall;
108
+ clearTimeout(timeout2);
109
+ if (delta >= delay2) {
110
+ cb(...args);
111
+ lastCall = now;
112
+ } else {
113
+ timeout2 = setTimeout(() => {
114
+ cb(...args);
115
+ lastCall = Date.now();
116
+ }, delay2 - delta);
117
+ }
95
118
  };
96
119
  };
97
120
 
@@ -126,8 +149,28 @@ var sleep = (ms) => {
126
149
  sleeper();
127
150
  });
128
151
  };
152
+ var sleepWithContext = (ctx, ms) => {
153
+ const error = new ContextDisposedError();
154
+ return new Promise((resolve, reject) => {
155
+ if (ctx.disposed) {
156
+ reject(error);
157
+ return;
158
+ }
159
+ const timeout2 = setTimeout(() => {
160
+ clearDispose();
161
+ resolve();
162
+ }, ms);
163
+ const clearDispose = ctx.onDispose(() => {
164
+ clearTimeout(timeout2);
165
+ reject(error);
166
+ });
167
+ });
168
+ };
129
169
  var asyncReturn = () => sleep(0);
130
170
  var asyncTimeout = async (promise, timeout2, err) => {
171
+ if (typeof promise === "function") {
172
+ throw new Error("First argument must be a promise.");
173
+ }
131
174
  let timeoutId;
132
175
  const throwable = err === void 0 || typeof err === "string" ? new TimeoutError(timeout2, err) : err;
133
176
  const timeoutPromise = new Promise((resolve, reject) => {
@@ -136,9 +179,8 @@ var asyncTimeout = async (promise, timeout2, err) => {
136
179
  }, timeout2);
137
180
  unrefTimeout(timeoutId);
138
181
  });
139
- const conditionTimeout = typeof promise === "function" ? createPromiseFromCallback(promise) : promise;
140
182
  return await Promise.race([
141
- conditionTimeout,
183
+ promise,
142
184
  timeoutPromise
143
185
  ]).finally(() => {
144
186
  clearTimeout(timeoutId);
@@ -149,23 +191,6 @@ var unrefTimeout = (timeoutId) => {
149
191
  timeoutId.unref();
150
192
  }
151
193
  };
152
- var sleepWithContext = (ctx, ms) => {
153
- const error = new ContextDisposedError();
154
- return new Promise((resolve, reject) => {
155
- if (ctx.disposed) {
156
- reject(error);
157
- return;
158
- }
159
- const timeout2 = setTimeout(() => {
160
- clearDispose();
161
- resolve();
162
- }, ms);
163
- const clearDispose = ctx.onDispose(() => {
164
- clearTimeout(timeout2);
165
- reject(error);
166
- });
167
- });
168
- };
169
194
 
170
195
  // src/event-emitter.ts
171
196
  var onEvent = (eventEmitter, eventName, callback) => {
@@ -192,13 +217,8 @@ var waitForEvent = (eventEmitter, eventName, test, timeout2, error) => {
192
217
 
193
218
  // src/events.ts
194
219
  import { Context } from "@dxos/context";
195
- var __dxlog_file = "/__w/dxos/dxos/packages/common/async/src/events.ts";
196
220
  var DO_NOT_ERROR_ON_ASYNC_CALLBACK = true;
197
221
  var Event = class _Event {
198
- constructor() {
199
- this._listeners = /* @__PURE__ */ new Set();
200
- this._effects = /* @__PURE__ */ new Set();
201
- }
202
222
  /**
203
223
  * Wrap objects that have on/off style event emitters.
204
224
  */
@@ -211,6 +231,8 @@ var Event = class _Event {
211
231
  });
212
232
  return event;
213
233
  }
234
+ _listeners = /* @__PURE__ */ new Set();
235
+ _effects = /* @__PURE__ */ new Set();
214
236
  /**
215
237
  * Emit an event.
216
238
  * In most cases should only be called by the class or entity containing the event.
@@ -249,10 +271,7 @@ var Event = class _Event {
249
271
  _ctx,
250
272
  _callback
251
273
  ] : [
252
- new Context(void 0, {
253
- F: __dxlog_file,
254
- L: 132
255
- }),
274
+ new Context(),
256
275
  _ctx
257
276
  ];
258
277
  const weak = !!options?.weak;
@@ -282,10 +301,7 @@ var Event = class _Event {
282
301
  _ctx,
283
302
  _callback
284
303
  ] : [
285
- new Context(void 0, {
286
- F: __dxlog_file,
287
- L: 169
288
- }),
304
+ new Context(),
289
305
  _ctx
290
306
  ];
291
307
  const listener = new EventListener(this, callback, ctx, true, false);
@@ -454,11 +470,15 @@ var Event = class _Event {
454
470
  }
455
471
  };
456
472
  var EventListener = class {
473
+ ctx;
474
+ once;
475
+ weak;
476
+ callback;
477
+ _clearDispose = void 0;
457
478
  constructor(event, listener, ctx, once, weak) {
458
479
  this.ctx = ctx;
459
480
  this.once = once;
460
481
  this.weak = weak;
461
- this._clearDispose = void 0;
462
482
  this._clearDispose = ctx.onDispose(() => {
463
483
  event._removeListener(this);
464
484
  });
@@ -518,65 +538,13 @@ var weakListeners = () => {
518
538
  };
519
539
  };
520
540
 
521
- // src/latch.ts
522
- import { invariant } from "@dxos/invariant";
523
- var __dxlog_file2 = "/__w/dxos/dxos/packages/common/async/src/latch.ts";
524
- var latch = ({ count = 1, timeout: timeout2 } = {}) => {
525
- invariant(count >= 0, void 0, {
526
- F: __dxlog_file2,
527
- L: 19,
528
- S: void 0,
529
- A: [
530
- "count >= 0",
531
- ""
532
- ]
533
- });
534
- let t;
535
- let doResolve;
536
- let doReject;
537
- const promise = new Promise((resolve, reject) => {
538
- doResolve = (value) => {
539
- clearTimeout(t);
540
- resolve(value);
541
- };
542
- doReject = (err) => {
543
- clearTimeout(t);
544
- reject(err);
545
- };
546
- });
547
- if (count === 0) {
548
- setTimeout(() => {
549
- doResolve(0);
550
- });
551
- } else {
552
- if (timeout2) {
553
- t = setTimeout(() => {
554
- doReject(new Error(`Timed out after ${timeout2.toLocaleString()}ms`));
555
- }, timeout2);
556
- }
557
- }
558
- let i = 0;
559
- return [
560
- async () => await promise,
561
- () => {
562
- if (++i === count) {
563
- doResolve(i);
564
- }
565
- return i;
566
- },
567
- (err) => doReject(err)
568
- ];
569
- };
570
-
571
541
  // src/mutex.ts
572
542
  import "@dxos/util";
573
543
  import { warnAfterTimeout } from "@dxos/debug";
574
544
  var Mutex = class {
575
- constructor() {
576
- this._queue = Promise.resolve();
577
- this._queueLength = 0;
578
- this._tag = null;
579
- }
545
+ _queue = Promise.resolve();
546
+ _queueLength = 0;
547
+ _tag = null;
580
548
  get tag() {
581
549
  return this._tag;
582
550
  }
@@ -622,6 +590,7 @@ var Mutex = class {
622
590
  }
623
591
  };
624
592
  var MutexGuard = class {
593
+ _release;
625
594
  constructor(_release) {
626
595
  this._release = _release;
627
596
  }
@@ -635,7 +604,7 @@ var MutexGuard = class {
635
604
  this.release();
636
605
  }
637
606
  };
638
- var classMutexSymbol = Symbol("class-mutex");
607
+ var classMutexSymbol = /* @__PURE__ */ Symbol("class-mutex");
639
608
  var FORCE_DISABLE_WARNING = false;
640
609
  var enableWarning = !FORCE_DISABLE_WARNING && globalThis.mochaExecutor;
641
610
  var synchronized = (target, propertyName, descriptor) => {
@@ -665,6 +634,7 @@ import Observable from "zen-observable";
665
634
  import PushStream from "zen-push";
666
635
 
667
636
  // src/trigger.ts
637
+ import { invariant } from "@dxos/invariant";
668
638
  var trigger = (timeout2) => {
669
639
  let callback;
670
640
  const promise = new Promise((resolve, reject) => {
@@ -680,18 +650,22 @@ var trigger = (timeout2) => {
680
650
  resolver
681
651
  ];
682
652
  };
683
- var TriggerState = /* @__PURE__ */ function(TriggerState2) {
653
+ var TriggerState = /* @__PURE__ */ (function(TriggerState2) {
684
654
  TriggerState2["WAITING"] = "WAITING";
685
655
  TriggerState2["RESOLVED"] = "RESOLVED";
686
656
  TriggerState2["REJECTED"] = "REJECTED";
687
657
  return TriggerState2;
688
- }({});
658
+ })({});
689
659
  var Trigger = class {
660
+ _options;
661
+ _promise;
662
+ _resolve;
663
+ _reject;
664
+ _state = "WAITING";
690
665
  constructor(_options = {
691
666
  autoReset: false
692
667
  }) {
693
668
  this._options = _options;
694
- this._state = "WAITING";
695
669
  this.reset();
696
670
  }
697
671
  get state() {
@@ -751,23 +725,53 @@ var Trigger = class {
751
725
  return this;
752
726
  }
753
727
  };
728
+ var latch = ({ count = 1, timeout: timeout2 } = {}) => {
729
+ invariant(count >= 0);
730
+ let t;
731
+ let doResolve;
732
+ let doReject;
733
+ const promise = new Promise((resolve, reject) => {
734
+ doResolve = (value) => {
735
+ clearTimeout(t);
736
+ resolve(value);
737
+ };
738
+ doReject = (err) => {
739
+ clearTimeout(t);
740
+ reject(err);
741
+ };
742
+ });
743
+ if (count === 0) {
744
+ setTimeout(() => {
745
+ doResolve(0);
746
+ });
747
+ } else {
748
+ if (timeout2) {
749
+ t = setTimeout(() => {
750
+ doReject(new Error(`Timed out after ${timeout2.toLocaleString()}ms`));
751
+ }, timeout2);
752
+ }
753
+ }
754
+ let i = 0;
755
+ return [
756
+ async () => await promise,
757
+ () => {
758
+ if (++i === count) {
759
+ doResolve(i);
760
+ }
761
+ return i;
762
+ },
763
+ (err) => doReject(err)
764
+ ];
765
+ };
754
766
 
755
767
  // src/observable.ts
756
768
  var MulticastObservable = class _MulticastObservable extends Observable {
769
+ _value;
770
+ _observers = /* @__PURE__ */ new Set();
771
+ _observable;
772
+ _completed = new Trigger();
757
773
  constructor(subscriber, _value) {
758
- super((observer) => this._subscribe(observer)), this._value = _value, this._observers = /* @__PURE__ */ new Set(), this._completed = new Trigger(), this._handlers = {
759
- next: (value) => {
760
- this._value = value;
761
- this._observers.forEach((observer) => observer.next?.(value));
762
- },
763
- error: (err) => {
764
- this._observers.forEach((observer) => observer.error?.(err));
765
- },
766
- complete: () => {
767
- this._completed.wake();
768
- this._observers.forEach((observer) => observer.complete?.());
769
- }
770
- };
774
+ super((observer) => this._subscribe(observer)), this._value = _value;
771
775
  this._observable = typeof subscriber === "function" ? new Observable(subscriber) : subscriber;
772
776
  this._observable.subscribe(this._handlers);
773
777
  }
@@ -851,18 +855,30 @@ var MulticastObservable = class _MulticastObservable extends Observable {
851
855
  this._observers.delete(observer);
852
856
  };
853
857
  }
858
+ _handlers = {
859
+ next: (value) => {
860
+ this._value = value;
861
+ this._observers.forEach((observer) => observer.next?.(value));
862
+ },
863
+ error: (err) => {
864
+ this._observers.forEach((observer) => observer.error?.(err));
865
+ },
866
+ complete: () => {
867
+ this._completed.wake();
868
+ this._observers.forEach((observer) => observer.complete?.());
869
+ }
870
+ };
854
871
  };
855
872
  var EMPTY_OBSERVABLE = MulticastObservable.of(null);
856
873
 
857
874
  // src/observable-value.ts
858
875
  import { createSetDispatch } from "@dxos/util";
859
876
  var ObservableProvider = class {
860
- constructor() {
861
- this._handlers = /* @__PURE__ */ new Set();
862
- this._proxy = createSetDispatch({
863
- handlers: this._handlers
864
- });
865
- }
877
+ _handlers = /* @__PURE__ */ new Set();
878
+ _proxy = createSetDispatch({
879
+ handlers: this._handlers
880
+ });
881
+ _value;
866
882
  /**
867
883
  * Proxy used to dispatch callbacks to each subscription.
868
884
  */
@@ -883,8 +899,10 @@ var ObservableProvider = class {
883
899
  }
884
900
  };
885
901
  var CancellableObservableProvider = class extends ObservableProvider {
902
+ _handleCancel;
903
+ _cancelled = false;
886
904
  constructor(_handleCancel) {
887
- super(), this._handleCancel = _handleCancel, this._cancelled = false;
905
+ super(), this._handleCancel = _handleCancel;
888
906
  }
889
907
  get cancelled() {
890
908
  return this._cancelled;
@@ -905,16 +923,15 @@ import { warnAfterTimeout as warnAfterTimeout2 } from "@dxos/debug";
905
923
  import { log as log2 } from "@dxos/log";
906
924
 
907
925
  // src/task-scheduling.ts
908
- import { ContextDisposedError as ContextDisposedError2 } from "@dxos/context";
926
+ import { Context as Context2, ContextDisposedError as ContextDisposedError2 } from "@dxos/context";
909
927
  import { StackTrace as StackTrace2 } from "@dxos/debug";
910
928
 
911
929
  // src/track-leaks.ts
912
930
  import { StackTrace } from "@dxos/debug";
913
931
  import { log } from "@dxos/log";
914
- var __dxlog_file3 = "/__w/dxos/dxos/packages/common/async/src/track-leaks.ts";
915
932
  var enabled = typeof process !== "undefined" && !!process.env.DX_TRACK_LEAKS;
916
933
  var openResources = /* @__PURE__ */ new Set();
917
- var handleSymbol = Symbol("checkLeaksHandle");
934
+ var handleSymbol = /* @__PURE__ */ Symbol("checkLeaksHandle");
918
935
  var trackResource = (resourceProvider) => {
919
936
  if (!enabled) {
920
937
  return () => {
@@ -961,31 +978,11 @@ var dumpLeaks = () => {
961
978
  if (!enabled) {
962
979
  return;
963
980
  }
964
- log.info(`Leaked resources ${openResources.size}:`, void 0, {
965
- F: __dxlog_file3,
966
- L: 82,
967
- S: void 0,
968
- C: (f, a) => f(...a)
969
- });
981
+ log.info(`Leaked resources ${openResources.size}:`);
970
982
  for (const resource of openResources) {
971
- log.info(`- ${resource.name} at`, void 0, {
972
- F: __dxlog_file3,
973
- L: 84,
974
- S: void 0,
975
- C: (f, a) => f(...a)
976
- });
977
- log.info(resource.openStack.getStack(1), void 0, {
978
- F: __dxlog_file3,
979
- L: 85,
980
- S: void 0,
981
- C: (f, a) => f(...a)
982
- });
983
- log.info("\n", void 0, {
984
- F: __dxlog_file3,
985
- L: 86,
986
- S: void 0,
987
- C: (f, a) => f(...a)
988
- });
983
+ log.info(`- ${resource.name} at`);
984
+ log.info(resource.openStack.getStack(1));
985
+ log.info("\n");
989
986
  }
990
987
  };
991
988
  if (enabled) {
@@ -994,12 +991,14 @@ if (enabled) {
994
991
 
995
992
  // src/task-scheduling.ts
996
993
  var DeferredTask = class {
994
+ _ctx;
995
+ _callback;
996
+ _scheduled = false;
997
+ _currentTask = null;
998
+ _nextTask = new Trigger();
997
999
  constructor(_ctx, _callback) {
998
1000
  this._ctx = _ctx;
999
1001
  this._callback = _callback;
1000
- this._scheduled = false;
1001
- this._currentTask = null;
1002
- this._nextTask = new Trigger();
1003
1002
  }
1004
1003
  get scheduled() {
1005
1004
  return this._scheduled;
@@ -1040,6 +1039,79 @@ var DeferredTask = class {
1040
1039
  await this._currentTask;
1041
1040
  }
1042
1041
  };
1042
+ var AsyncTask = class {
1043
+ #callback;
1044
+ #ctx = void 0;
1045
+ #scheduled = false;
1046
+ #currentTask = null;
1047
+ #nextTask = new Trigger();
1048
+ constructor(callback) {
1049
+ this.#callback = callback;
1050
+ }
1051
+ get scheduled() {
1052
+ return this.#scheduled;
1053
+ }
1054
+ /**
1055
+ * Context of the resource that owns the task.
1056
+ * When the context is disposed, the task is cancelled and cannot be scheduled again.
1057
+ */
1058
+ open() {
1059
+ this.#ctx = new Context2();
1060
+ }
1061
+ /**
1062
+ * Closes the task and waits for it to finish if it is running.
1063
+ */
1064
+ async close() {
1065
+ await this.#ctx?.dispose();
1066
+ await this.join();
1067
+ this.#ctx = void 0;
1068
+ }
1069
+ [Symbol.asyncDispose]() {
1070
+ return this.close();
1071
+ }
1072
+ /**
1073
+ * Schedule the task to run asynchronously.
1074
+ */
1075
+ // TODO(dmaretskyi): Add scheduleAt. Where the earlier time will override the later one.
1076
+ schedule() {
1077
+ if (!this.#ctx || this.#ctx.disposed) {
1078
+ throw new Error("AsyncTask not open");
1079
+ }
1080
+ if (this.#scheduled) {
1081
+ return;
1082
+ }
1083
+ scheduleTask(this.#ctx, async () => {
1084
+ await this.#currentTask;
1085
+ if (!this.#ctx || this.#ctx.disposed) {
1086
+ return;
1087
+ }
1088
+ this.#scheduled = false;
1089
+ const completionTrigger = this.#nextTask;
1090
+ this.#nextTask = new Trigger();
1091
+ this.#currentTask = runInContextAsync(this.#ctx, () => this.#callback()).then(() => {
1092
+ completionTrigger.wake();
1093
+ });
1094
+ });
1095
+ this.#scheduled = true;
1096
+ }
1097
+ /**
1098
+ * Schedule the task to run and wait for it to finish.
1099
+ */
1100
+ async runBlocking() {
1101
+ if (this.#ctx?.disposed) {
1102
+ throw new ContextDisposedError2();
1103
+ }
1104
+ this.schedule();
1105
+ await this.#nextTask.wait();
1106
+ }
1107
+ /**
1108
+ * Waits for the current task to finish if it is running.
1109
+ * Does not schedule a new task.
1110
+ */
1111
+ async join() {
1112
+ await this.#currentTask;
1113
+ }
1114
+ };
1043
1115
  var runInContext = (ctx, fn) => {
1044
1116
  try {
1045
1117
  fn();
@@ -1125,15 +1197,18 @@ function _ts_decorate(decorators, target, key, desc) {
1125
1197
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1126
1198
  return c > 3 && r && Object.defineProperty(target, key, r), r;
1127
1199
  }
1128
- var __dxlog_file4 = "/__w/dxos/dxos/packages/common/async/src/persistent-lifecycle.ts";
1129
1200
  var INIT_RESTART_DELAY = 100;
1130
1201
  var DEFAULT_MAX_RESTART_DELAY = 5e3;
1131
1202
  var PersistentLifecycle = class extends Resource {
1203
+ _start;
1204
+ _stop;
1205
+ _onRestart;
1206
+ _maxRestartDelay;
1207
+ _currentState = void 0;
1208
+ _restartTask = void 0;
1209
+ _restartAfter = 0;
1132
1210
  constructor({ start, stop, onRestart, maxRestartDelay = DEFAULT_MAX_RESTART_DELAY }) {
1133
1211
  super();
1134
- this._currentState = void 0;
1135
- this._restartTask = void 0;
1136
- this._restartAfter = 0;
1137
1212
  this._start = start;
1138
1213
  this._stop = stop;
1139
1214
  this._onRestart = onRestart;
@@ -1149,11 +1224,6 @@ var PersistentLifecycle = class extends Resource {
1149
1224
  } catch (err) {
1150
1225
  log2.warn("Restart failed", {
1151
1226
  err
1152
- }, {
1153
- F: __dxlog_file4,
1154
- L: 72,
1155
- S: this,
1156
- C: (f, a) => f(...a)
1157
1227
  });
1158
1228
  this._restartTask?.schedule();
1159
1229
  }
@@ -1161,11 +1231,6 @@ var PersistentLifecycle = class extends Resource {
1161
1231
  this._currentState = await this._start().catch((err) => {
1162
1232
  log2.warn("Start failed", {
1163
1233
  err
1164
- }, {
1165
- F: __dxlog_file4,
1166
- L: 78,
1167
- S: this,
1168
- C: (f, a) => f(...a)
1169
1234
  });
1170
1235
  this._restartTask?.schedule();
1171
1236
  return void 0;
@@ -1179,11 +1244,6 @@ var PersistentLifecycle = class extends Resource {
1179
1244
  async _restart() {
1180
1245
  log2(`restarting in ${this._restartAfter}ms`, {
1181
1246
  state: this._lifecycleState
1182
- }, {
1183
- F: __dxlog_file4,
1184
- L: 91,
1185
- S: this,
1186
- C: (f, a) => f(...a)
1187
1247
  });
1188
1248
  await this._stopCurrentState();
1189
1249
  if (this._lifecycleState !== LifecycleState.OPEN) {
@@ -1202,12 +1262,7 @@ var PersistentLifecycle = class extends Resource {
1202
1262
  try {
1203
1263
  await this._stop(this._currentState);
1204
1264
  } catch (err) {
1205
- log2.catch(err, void 0, {
1206
- F: __dxlog_file4,
1207
- L: 113,
1208
- S: this,
1209
- C: (f, a) => f(...a)
1210
- });
1265
+ log2.catch(err);
1211
1266
  }
1212
1267
  this._currentState = void 0;
1213
1268
  }
@@ -1231,7 +1286,6 @@ _ts_decorate([
1231
1286
 
1232
1287
  // src/push-iterable.ts
1233
1288
  import { invariant as invariant2 } from "@dxos/invariant";
1234
- var __dxlog_file5 = "/__w/dxos/dxos/packages/common/async/src/push-iterable.ts";
1235
1289
  var makePushIterable = () => {
1236
1290
  const buf = [];
1237
1291
  const trigger2 = new Trigger({
@@ -1245,15 +1299,7 @@ var makePushIterable = () => {
1245
1299
  await trigger2.wait();
1246
1300
  }
1247
1301
  const item = buf.shift();
1248
- invariant2(item, void 0, {
1249
- F: __dxlog_file5,
1250
- L: 42,
1251
- S: this,
1252
- A: [
1253
- "item",
1254
- ""
1255
- ]
1256
- });
1302
+ invariant2(item);
1257
1303
  switch (item.kind) {
1258
1304
  case "next":
1259
1305
  return {
@@ -1295,20 +1341,6 @@ var makePushIterable = () => {
1295
1341
  };
1296
1342
  };
1297
1343
 
1298
- // src/sink.ts
1299
- var sink = (emitter, event, count = 1) => {
1300
- const [getPromise, resolve] = trigger();
1301
- let counter = 0;
1302
- const listener = () => {
1303
- if (++counter === count) {
1304
- emitter.off(event, listener);
1305
- resolve();
1306
- }
1307
- };
1308
- emitter.on(event, listener);
1309
- return getPromise();
1310
- };
1311
-
1312
1344
  // src/stream-to-array.ts
1313
1345
  var streamToArray = (stream) => {
1314
1346
  let deferred;
@@ -1354,11 +1386,6 @@ var streamToArray = (stream) => {
1354
1386
  // src/test-stream.ts
1355
1387
  import { Duplex } from "node:stream";
1356
1388
  var TestStream = class extends Duplex {
1357
- constructor() {
1358
- super(...arguments);
1359
- this._received = Buffer.alloc(0);
1360
- this._onWrite = new Event();
1361
- }
1362
1389
  static async assertConnectivity(stream1, stream2, { timeout: timeout2 = 200 } = {}) {
1363
1390
  stream1.push("ping");
1364
1391
  stream2.push("pong");
@@ -1371,6 +1398,8 @@ var TestStream = class extends Duplex {
1371
1398
  })
1372
1399
  ]);
1373
1400
  }
1401
+ _received = Buffer.alloc(0);
1402
+ _onWrite = new Event();
1374
1403
  _write(chunk, encoding, callback) {
1375
1404
  this._received = Buffer.concat([
1376
1405
  this._received,
@@ -1412,13 +1441,48 @@ var waitForCondition = ({ condition, timeout: timeout2 = 0, interval: interval2
1412
1441
  timeout: timeout2
1413
1442
  });
1414
1443
  };
1444
+ var until = (cb, timeout2) => {
1445
+ return new Promise((resolve, reject) => {
1446
+ const t = timeout2 && setTimeout(() => {
1447
+ reject(new Error(`Timeout after ${t}ms`));
1448
+ }, timeout2);
1449
+ setTimeout(async () => {
1450
+ try {
1451
+ await cb((value) => {
1452
+ t && clearTimeout(t);
1453
+ resolve(value);
1454
+ }, (error) => {
1455
+ t && clearTimeout(t);
1456
+ reject(error);
1457
+ });
1458
+ } catch (err) {
1459
+ reject(err);
1460
+ }
1461
+ });
1462
+ });
1463
+ };
1464
+ var untilPromise = (cb) => cb();
1465
+ var untilError = (cb) => {
1466
+ return new Promise((resolve, reject) => {
1467
+ setTimeout(async () => {
1468
+ try {
1469
+ await cb();
1470
+ reject(new Error("No error was thrown."));
1471
+ } catch (err) {
1472
+ resolve(err);
1473
+ }
1474
+ });
1475
+ });
1476
+ };
1415
1477
 
1416
1478
  // src/timer.ts
1417
1479
  var Timer = class {
1480
+ _callback;
1481
+ _state = new Event();
1482
+ _timer;
1483
+ _count = 0;
1418
1484
  constructor(_callback) {
1419
1485
  this._callback = _callback;
1420
- this._state = new Event();
1421
- this._count = 0;
1422
1486
  }
1423
1487
  get state() {
1424
1488
  return this._state;
@@ -1461,51 +1525,23 @@ var Timer = class {
1461
1525
  }
1462
1526
  };
1463
1527
 
1464
- // src/until.ts
1465
- var until = (cb, timeout2) => {
1466
- return new Promise((resolve, reject) => {
1467
- const t = timeout2 && setTimeout(() => {
1468
- reject(new Error(`Timeout after ${t}ms`));
1469
- }, timeout2);
1470
- setTimeout(async () => {
1471
- try {
1472
- await cb((value) => {
1473
- t && clearTimeout(t);
1474
- resolve(value);
1475
- }, (error) => {
1476
- t && clearTimeout(t);
1477
- reject(error);
1478
- });
1479
- } catch (err) {
1480
- reject(err);
1481
- }
1482
- });
1483
- });
1484
- };
1485
- var untilPromise = (cb) => cb();
1486
- var untilError = (cb) => {
1487
- return new Promise((resolve, reject) => {
1488
- setTimeout(async () => {
1489
- try {
1490
- await cb();
1491
- reject(new Error("No error was thrown."));
1492
- } catch (err) {
1493
- resolve(err);
1494
- }
1495
- });
1496
- });
1497
- };
1498
-
1499
1528
  // src/update-scheduler.ts
1500
1529
  var TIME_PERIOD = 1e3;
1501
1530
  var UpdateScheduler = class {
1531
+ _ctx;
1532
+ _callback;
1533
+ _params;
1534
+ /**
1535
+ * Promise that resolves when the callback is done.
1536
+ * Never rejects.
1537
+ */
1538
+ _promise = null;
1539
+ _scheduled = false;
1540
+ _lastUpdateTime = -TIME_PERIOD;
1502
1541
  constructor(_ctx, _callback, _params = {}) {
1503
1542
  this._ctx = _ctx;
1504
1543
  this._callback = _callback;
1505
1544
  this._params = _params;
1506
- this._promise = null;
1507
- this._scheduled = false;
1508
- this._lastUpdateTime = -TIME_PERIOD;
1509
1545
  _ctx.onDispose(async () => {
1510
1546
  await this._promise;
1511
1547
  });
@@ -1518,13 +1554,13 @@ var UpdateScheduler = class {
1518
1554
  await this._promise;
1519
1555
  if (this._params.maxFrequency) {
1520
1556
  const now = performance.now();
1521
- const delay = this._lastUpdateTime + TIME_PERIOD / this._params.maxFrequency - now;
1522
- if (delay > 0) {
1557
+ const delay2 = this._lastUpdateTime + TIME_PERIOD / this._params.maxFrequency - now;
1558
+ if (delay2 > 0) {
1523
1559
  await new Promise((resolve) => {
1524
1560
  const timeoutId = setTimeout(() => {
1525
1561
  clearContext();
1526
1562
  resolve();
1527
- }, delay);
1563
+ }, delay2);
1528
1564
  const clearContext = this._ctx.onDispose(() => {
1529
1565
  clearTimeout(timeoutId);
1530
1566
  resolve();
@@ -1568,6 +1604,7 @@ var UpdateScheduler = class {
1568
1604
  }
1569
1605
  };
1570
1606
  export {
1607
+ AsyncTask,
1571
1608
  CancellableObservableProvider,
1572
1609
  DeferredTask,
1573
1610
  Event,
@@ -1588,26 +1625,26 @@ export {
1588
1625
  UpdateScheduler,
1589
1626
  addEventListener,
1590
1627
  addListener,
1591
- asyncChain,
1592
1628
  asyncReturn,
1593
1629
  asyncTimeout,
1630
+ chain,
1594
1631
  combine,
1595
- createPromiseFromCallback,
1596
1632
  debounce,
1597
1633
  debounceAndThrottle,
1634
+ delay,
1598
1635
  dumpLeaks,
1599
1636
  interval,
1600
1637
  latch,
1601
1638
  makePushIterable,
1602
1639
  observableError,
1603
1640
  onEvent,
1641
+ promiseFromCallback,
1604
1642
  runInContext,
1605
1643
  runInContextAsync,
1606
1644
  scheduleExponentialBackoffTaskInterval,
1607
1645
  scheduleMicroTask,
1608
1646
  scheduleTask,
1609
1647
  scheduleTaskInterval,
1610
- sink,
1611
1648
  sleep,
1612
1649
  sleepWithContext,
1613
1650
  streamToArray,