atom.io 0.33.20 → 0.34.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.
Files changed (31) hide show
  1. package/dist/internal/index.d.ts +5 -6
  2. package/dist/internal/index.d.ts.map +1 -1
  3. package/dist/internal/index.js +1257 -1249
  4. package/dist/internal/index.js.map +1 -1
  5. package/dist/react/index.js +22 -11
  6. package/dist/react/index.js.map +1 -1
  7. package/dist/realtime-client/index.js +2 -2
  8. package/dist/realtime-client/index.js.map +1 -1
  9. package/dist/realtime-testing/index.d.ts.map +1 -1
  10. package/dist/realtime-testing/index.js +0 -1
  11. package/dist/realtime-testing/index.js.map +1 -1
  12. package/package.json +2 -2
  13. package/src/internal/atom/create-regular-atom.ts +6 -7
  14. package/src/internal/caching.ts +10 -9
  15. package/src/internal/future.ts +3 -0
  16. package/src/internal/get-state/read-or-compute-value.ts +12 -7
  17. package/src/internal/mutable/create-mutable-atom.ts +2 -4
  18. package/src/internal/selector/create-readonly-held-selector.ts +10 -0
  19. package/src/internal/selector/create-readonly-pure-selector.ts +13 -4
  20. package/src/internal/selector/create-writable-held-selector.ts +11 -2
  21. package/src/internal/selector/create-writable-pure-selector.ts +11 -1
  22. package/src/internal/selector/trace-selector-atoms.ts +18 -40
  23. package/src/internal/selector/update-selector-atoms.ts +5 -5
  24. package/src/internal/set-state/evict-downstream.ts +2 -2
  25. package/src/internal/set-state/reset-atom-or-selector.ts +3 -3
  26. package/src/internal/store/store.ts +0 -1
  27. package/src/internal/subscribe/subscribe-to-root-atoms.ts +42 -38
  28. package/src/internal/subscribe/subscribe-to-state.ts +23 -11
  29. package/src/react/use-loadable.ts +18 -13
  30. package/src/realtime-client/realtime-client-stores/client-sync-store.ts +2 -2
  31. package/src/realtime-testing/setup-realtime-test.tsx +0 -5
@@ -8,61 +8,6 @@ function arbitrary(random = Math.random) {
8
8
  return random().toString(36).slice(2);
9
9
  }
10
10
 
11
- //#endregion
12
- //#region src/internal/future.ts
13
- /**
14
- * A Promise whose incoming value can be hot swapped.
15
- * @internal
16
- * @private
17
- * @typeParam T The type of the value that the promise will resolve to.
18
- *
19
- * @remarks
20
- * Can be constructed like a Promise, or from an existing Promise.
21
- */
22
- var Future = class extends Promise {
23
- fate;
24
- resolve;
25
- reject;
26
- done = false;
27
- constructor(executor) {
28
- let superResolve;
29
- let superReject;
30
- super((resolve, reject) => {
31
- superResolve = resolve;
32
- superReject = reject;
33
- });
34
- this.resolve = superResolve;
35
- this.reject = superReject;
36
- this.use(executor instanceof Promise ? executor : new Promise(executor));
37
- }
38
- pass(promise, value) {
39
- if (promise === this.fate) {
40
- this.resolve(value);
41
- this.done = true;
42
- }
43
- }
44
- fail(promise, reason) {
45
- if (promise === this.fate) {
46
- this.reject(reason);
47
- this.done = true;
48
- }
49
- }
50
- use(value) {
51
- if (value instanceof Promise) {
52
- const promise = value;
53
- this.fate = promise;
54
- promise.then((resolved) => {
55
- this.pass(promise, resolved);
56
- }, (reason) => {
57
- this.fail(promise, reason);
58
- });
59
- } else {
60
- this.resolve(value);
61
- this.fate = void 0;
62
- }
63
- }
64
- };
65
-
66
11
  //#endregion
67
12
  //#region src/internal/lineage.ts
68
13
  function newest(scion) {
@@ -432,85 +377,107 @@ var StatefulSubject = class extends Subject {
432
377
  };
433
378
 
434
379
  //#endregion
435
- //#region src/internal/transaction/is-root-store.ts
436
- function isRootStore(store) {
437
- return `epoch` in store.transactionMeta;
438
- }
439
- function isChildStore(store) {
440
- return `phase` in store.transactionMeta;
441
- }
442
-
443
- //#endregion
444
- //#region src/internal/transaction/abort-transaction.ts
445
- const abortTransaction = (store) => {
380
+ //#region src/internal/subscribe/recall-state.ts
381
+ const recallState = (store, state) => {
446
382
  const target = newest(store);
447
- if (!isChildStore(target)) {
448
- store.logger.warn(`🐞`, `transaction`, `???`, `abortTransaction called outside of a transaction. This is probably a bug in AtomIO.`);
449
- return;
450
- }
451
- store.logger.info(`🪂`, `transaction`, target.transactionMeta.update.key, `Aborting transaction`);
452
- target.parent.child = null;
383
+ if (target.operation.open) return target.operation.prev.get(state.key);
384
+ return target.valueMap.get(state.key);
453
385
  };
454
386
 
455
387
  //#endregion
456
- //#region src/internal/capitalize.ts
457
- function capitalize(string) {
458
- return string[0].toUpperCase() + string.slice(1);
459
- }
460
-
461
- //#endregion
462
- //#region src/internal/pretty-print.ts
463
- function prettyPrintTokenType(token) {
464
- return token.type.split(`_`).map(capitalize).join(` `);
388
+ //#region src/internal/subscribe/subscribe-in-store.ts
389
+ function subscribeInStore(store, token, handleUpdate, key = arbitrary$1()) {
390
+ switch (token.type) {
391
+ case `atom`:
392
+ case `mutable_atom`:
393
+ case `readonly_pure_selector`:
394
+ case `readonly_held_selector`:
395
+ case `writable_pure_selector`:
396
+ case `writable_held_selector`: return subscribeToState$1(store, token, key, handleUpdate);
397
+ case `transaction`: return subscribeToTransaction$1(store, token, key, handleUpdate);
398
+ case `timeline`: return subscribeToTimeline$1(store, token, key, handleUpdate);
399
+ }
465
400
  }
466
401
 
467
402
  //#endregion
468
- //#region src/internal/not-found-error.ts
469
- var NotFoundError = class extends Error {
470
- constructor(token, store) {
471
- super(`${prettyPrintTokenType(token)} ${stringifyJson(token.key)} not found in store "${store.config.name}".`);
403
+ //#region src/internal/future.ts
404
+ /**
405
+ * A Promise whose incoming value can be hot swapped.
406
+ * @internal
407
+ * @private
408
+ * @typeParam T The type of the value that the promise will resolve to.
409
+ *
410
+ * @remarks
411
+ * Can be constructed like a Promise, or from an existing Promise.
412
+ */
413
+ var Future = class extends Promise {
414
+ fate;
415
+ resolve;
416
+ reject;
417
+ done = false;
418
+ constructor(executor) {
419
+ let superResolve;
420
+ let superReject;
421
+ super((resolve, reject) => {
422
+ superResolve = resolve;
423
+ superReject = reject;
424
+ });
425
+ this.resolve = superResolve;
426
+ this.reject = superReject;
427
+ this.use(executor instanceof Promise ? executor : new Promise(executor));
428
+ }
429
+ pass(promise, value) {
430
+ if (promise === this.fate) {
431
+ this.resolve(value);
432
+ this.done = true;
433
+ }
434
+ }
435
+ fail(promise, reason) {
436
+ if (promise === this.fate) {
437
+ this.reject(reason);
438
+ this.done = true;
439
+ }
440
+ }
441
+ use(value) {
442
+ if (this === value) return;
443
+ if (value instanceof Promise) {
444
+ const promise = value;
445
+ this.fate = promise;
446
+ promise.then((resolved) => {
447
+ this.pass(promise, resolved);
448
+ }, (reason) => {
449
+ this.fail(promise, reason);
450
+ });
451
+ } else {
452
+ this.resolve(value);
453
+ this.fate = void 0;
454
+ }
472
455
  }
473
456
  };
474
457
 
475
458
  //#endregion
476
- //#region src/internal/transaction/act-upon-store.ts
477
- function actUponStore(store, token, id) {
478
- return (...parameters) => {
479
- const tx = withdraw(store, token);
480
- if (tx) return tx.run(parameters, id);
481
- throw new NotFoundError(token, store);
482
- };
459
+ //#region src/internal/set-state/copy-mutable-if-needed.ts
460
+ function copyMutableIfNeeded(target, atom$1, origin) {
461
+ const originValue = origin.valueMap.get(atom$1.key);
462
+ const targetValue = target.valueMap.get(atom$1.key);
463
+ if (originValue !== targetValue) return targetValue;
464
+ if (originValue === void 0) return atom$1.default();
465
+ origin.logger.info(`📃`, `atom`, atom$1.key, `copying`);
466
+ const jsonValue = atom$1.toJson(originValue);
467
+ const copiedValue = atom$1.fromJson(jsonValue);
468
+ target.valueMap.set(atom$1.key, copiedValue);
469
+ new Tracker(atom$1, origin);
470
+ return copiedValue;
483
471
  }
484
472
 
485
473
  //#endregion
486
- //#region src/internal/set-state/become.ts
487
- const become = (nextVersionOfThing) => (originalThing) => nextVersionOfThing instanceof Function ? nextVersionOfThing(originalThing) : nextVersionOfThing;
488
-
489
- //#endregion
490
- //#region src/internal/get-state/read-or-compute-value.ts
491
- const readOrComputeValue = (target, state) => {
492
- if (target.valueMap.has(state.key)) {
493
- target.logger.info(`📖`, state.type, state.key, `reading cached value`);
494
- return readCachedValue(state, target);
495
- }
496
- switch (state.type) {
497
- case `readonly_held_selector`:
498
- case `readonly_pure_selector`:
499
- case `writable_held_selector`:
500
- case `writable_pure_selector`:
501
- target.logger.info(`🧮`, state.type, state.key, `computing value`);
502
- return state.get();
503
- case `atom`:
504
- case `mutable_atom`: {
505
- const def = state.default;
506
- let fallback;
507
- if (def instanceof Function) fallback = def();
508
- else fallback = def;
509
- target.logger.info(`💁`, `atom`, state.key, `could not find cached value; using default`, fallback);
510
- return fallback;
511
- }
512
- }
513
- };
474
+ //#region src/internal/transaction/is-root-store.ts
475
+ function isRootStore(store) {
476
+ return `epoch` in store.transactionMeta;
477
+ }
478
+ function isChildStore(store) {
479
+ return `phase` in store.transactionMeta;
480
+ }
514
481
 
515
482
  //#endregion
516
483
  //#region src/internal/operation.ts
@@ -549,22 +516,6 @@ const markDone = (store, key) => {
549
516
  store.operation.done.add(key);
550
517
  };
551
518
 
552
- //#endregion
553
- //#region src/internal/set-state/emit-update.ts
554
- const emitUpdate = (store, state, update) => {
555
- switch (state.type) {
556
- case `mutable_atom`:
557
- store.logger.info(`📢`, state.type, state.key, `is now (`, update.newValue, `) subscribers:`, state.subject.subscribers);
558
- break;
559
- case `atom`:
560
- case `writable_pure_selector`:
561
- case `readonly_pure_selector`:
562
- case `writable_held_selector`:
563
- case `readonly_held_selector`: store.logger.info(`📢`, state.type, state.key, `went (`, update.oldValue, `->`, update.newValue, `) subscribers:`, state.subject.subscribers);
564
- }
565
- state.subject.next(update);
566
- };
567
-
568
519
  //#endregion
569
520
  //#region src/internal/set-state/evict-downstream.ts
570
521
  function evictDownStream(store, atom$1) {
@@ -575,7 +526,7 @@ function evictDownStream(store, atom$1) {
575
526
  if (target.operation.open) target.logger.info(`🧹`, atom$1.type, atom$1.key, `[ ${[...target.operation.done].join(`, `)} ] already done`);
576
527
  for (const key of downstreamKeys) {
577
528
  if (isDone(target, key)) continue;
578
- evictCachedValue(key, target);
529
+ evictCachedValue(target, key);
579
530
  markDone(target, key);
580
531
  }
581
532
  }
@@ -585,81 +536,117 @@ function evictDownStreamFromSelector(store, selector) {
585
536
  const relationEntries = target.selectorGraph.getRelationEntries({ upstreamSelectorKey: selector.key }).filter(([_, { source }]) => source === selector.key);
586
537
  for (const [downstreamSelectorKey] of relationEntries) {
587
538
  if (isDone(target, downstreamSelectorKey)) continue;
588
- evictCachedValue(downstreamSelectorKey, target);
539
+ evictCachedValue(target, downstreamSelectorKey);
589
540
  markDone(target, downstreamSelectorKey);
590
541
  }
591
542
  }
592
543
 
593
544
  //#endregion
594
- //#region src/internal/set-state/set-atom.ts
595
- const setAtom = (target, atom$1, next) => {
596
- const oldValue = readOrComputeValue(target, atom$1);
597
- let newValue = oldValue;
598
- if (atom$1.type === `mutable_atom` && isChildStore(target)) {
599
- const { parent } = target;
600
- const copiedValue = copyMutableIfNeeded(target, atom$1, parent);
601
- newValue = copiedValue;
602
- }
603
- newValue = become(next)(newValue);
604
- target.logger.info(`📝`, `atom`, atom$1.key, `set to`, newValue);
605
- newValue = cacheValue(target, atom$1.key, newValue, atom$1.subject);
606
- markDone(target, atom$1.key);
607
- evictDownStream(target, atom$1);
608
- const update = {
609
- oldValue,
610
- newValue
611
- };
612
- if (!isChildStore(target)) {
613
- emitUpdate(target, atom$1, update);
614
- return;
545
+ //#region src/internal/caching.ts
546
+ function cacheValue(target, key, value, subject) {
547
+ const currentValue = target.valueMap.get(key);
548
+ if (currentValue instanceof Future && !currentValue.done) {
549
+ const future = currentValue;
550
+ if (value instanceof Promise) {
551
+ future.use(value);
552
+ return future;
553
+ }
554
+ target.valueMap.set(key, value);
555
+ return value;
615
556
  }
616
- if (target.on.transactionApplying.state === null) {
617
- const { key } = atom$1;
618
- if (isTransceiver(update.newValue)) return;
619
- const atomUpdate = {
620
- type: `atom_update`,
621
- key,
622
- ...update
623
- };
624
- if (atom$1.family) atomUpdate.family = atom$1.family;
625
- target.transactionMeta.update.updates.push(atomUpdate);
626
- target.logger.info(`📁`, `atom`, key, `stowed (`, update.oldValue, `->`, update.newValue, `)`);
627
- } else if (atom$1.key.startsWith(`*`)) {
628
- const mutableKey = atom$1.key.slice(1);
629
- const mutableAtom = target.atoms.get(mutableKey);
630
- let transceiver = target.valueMap.get(mutableKey);
631
- if (mutableAtom.type === `mutable_atom` && isChildStore(target)) {
632
- const { parent } = target;
633
- const copiedValue = copyMutableIfNeeded(target, mutableAtom, parent);
634
- transceiver = copiedValue;
635
- }
636
- const accepted = transceiver.do(update.newValue) === null;
637
- if (accepted) evictDownStream(target, mutableAtom);
557
+ if (value instanceof Promise) {
558
+ const future = new Future(value);
559
+ target.valueMap.set(key, future);
560
+ future.then(function handleResolvedFuture(resolved) {
561
+ const current = target.valueMap.get(key);
562
+ if (current === future) {
563
+ cacheValue(target, key, resolved, subject);
564
+ const atom$1 = target.atoms.get(key);
565
+ if (atom$1) {
566
+ openOperation(target, atom$1);
567
+ evictDownStream(target, atom$1);
568
+ closeOperation(target);
569
+ } else {
570
+ const selector = target.writableSelectors.get(key) ?? target.readonlySelectors.get(key);
571
+ if (selector) {
572
+ openOperation(target, selector);
573
+ evictDownStreamFromSelector(target, selector);
574
+ closeOperation(target);
575
+ }
576
+ }
577
+ subject.next({
578
+ newValue: resolved,
579
+ oldValue: future
580
+ });
581
+ }
582
+ }).catch((thrown) => {
583
+ target.logger.error(`💥`, `state`, key, `rejected:`, thrown);
584
+ });
585
+ return future;
586
+ }
587
+ target.valueMap.set(key, value);
588
+ return value;
589
+ }
590
+ const readCachedValue = (state, target) => {
591
+ target.logger.info(`📖`, state.type, state.key, `reading cached value`);
592
+ let value = target.valueMap.get(state.key);
593
+ if (state.type === `mutable_atom` && isChildStore(target)) {
594
+ const { parent } = target;
595
+ const copiedValue = copyMutableIfNeeded(target, state, parent);
596
+ value = copiedValue;
597
+ }
598
+ return value;
599
+ };
600
+ const evictCachedValue = (target, key) => {
601
+ const currentValue = target.valueMap.get(key);
602
+ if (currentValue instanceof Future) {
603
+ const selector = target.writableSelectors.get(key) ?? target.readonlySelectors.get(key);
604
+ if (selector) selector.get();
605
+ return;
638
606
  }
607
+ if (target.operation.open) target.operation.prev.set(key, currentValue);
608
+ target.valueMap.delete(key);
609
+ target.logger.info(`🗑`, `state`, key, `evicted`);
639
610
  };
640
611
 
641
612
  //#endregion
642
- //#region src/internal/set-state/reset-atom-or-selector.ts
643
- function resetAtom(store, state) {
644
- let def = state.default;
645
- if (def instanceof Function) def = def();
646
- setAtom(store, state, def);
647
- }
648
- function resetAtomOrSelector(store, state) {
613
+ //#region src/internal/get-state/read-or-compute-value.ts
614
+ const readOrComputeValue = (target, state) => {
615
+ if (target.valueMap.has(state.key)) return readCachedValue(state, target);
649
616
  switch (state.type) {
650
- case `atom`:
651
- case `mutable_atom`:
652
- resetAtom(store, state);
653
- break;
654
- case `writable_pure_selector`:
617
+ case `readonly_held_selector`:
618
+ case `readonly_pure_selector`:
655
619
  case `writable_held_selector`:
656
- {
657
- const atoms = traceAllSelectorAtoms(state, store);
658
- for (const atom$1 of atoms) resetAtom(store, atom$1);
659
- }
660
- break;
620
+ case `writable_pure_selector`:
621
+ target.logger.info(`🧮`, state.type, state.key, `computing value`);
622
+ return state.get();
623
+ case `atom`:
624
+ case `mutable_atom`: {
625
+ const def = state.default;
626
+ let defaultValue;
627
+ if (def instanceof Function) defaultValue = def();
628
+ else defaultValue = def;
629
+ const cachedValue = cacheValue(target, state.key, defaultValue, state.subject);
630
+ target.logger.info(`💁`, `atom`, state.key, `could not find cached value; using default`, defaultValue);
631
+ return cachedValue;
632
+ }
661
633
  }
662
- }
634
+ };
635
+
636
+ //#endregion
637
+ //#region src/internal/subscribe/subscribe-to-root-atoms.ts
638
+ const subscribeToRootDependency = (target, selector, atom$1) => {
639
+ return atom$1.subject.subscribe(`${selector.type}:${selector.key}`, (atomChange) => {
640
+ target.logger.info(`📢`, selector.type, selector.key, `root`, atom$1.key, `went`, atomChange.oldValue, `->`, atomChange.newValue);
641
+ const oldValue = recallState(target, selector);
642
+ const newValue = readOrComputeValue(target, selector);
643
+ target.logger.info(`✨`, selector.type, selector.key, `went`, oldValue, `->`, newValue);
644
+ selector.subject.next({
645
+ newValue,
646
+ oldValue
647
+ });
648
+ });
649
+ };
663
650
 
664
651
  //#endregion
665
652
  //#region src/internal/families/create-regular-atom-family.ts
@@ -711,68 +698,258 @@ function createAtomFamily(store, options) {
711
698
  }
712
699
 
713
700
  //#endregion
714
- //#region src/internal/keys.ts
715
- const isAtomKey = (store, key) => newest(store).atoms.has(key);
716
- const isSelectorKey = (store, key) => newest(store).writableSelectors.has(key);
717
- const isReadonlySelectorKey = (store, key) => newest(store).readonlySelectors.has(key);
718
- const isStateKey = (store, key) => isAtomKey(store, key) || isSelectorKey(store, key) || isReadonlySelectorKey(store, key);
701
+ //#region src/internal/set-state/become.ts
702
+ const become = (nextVersionOfThing) => (originalThing) => nextVersionOfThing instanceof Function ? nextVersionOfThing(originalThing) : nextVersionOfThing;
719
703
 
720
704
  //#endregion
721
- //#region src/internal/selector/get-selector-dependency-keys.ts
722
- const getSelectorDependencyKeys = (store, key) => {
723
- const sources = newest(store).selectorGraph.getRelationEntries({ downstreamSelectorKey: key }).filter(([_, { source }]) => source !== key).map(([_, { source }]) => source).filter((source) => isStateKey(store, source));
724
- return sources;
705
+ //#region src/internal/set-state/emit-update.ts
706
+ const emitUpdate = (store, state, update) => {
707
+ switch (state.type) {
708
+ case `mutable_atom`:
709
+ store.logger.info(`📢`, state.type, state.key, `is now (`, update.newValue, `) subscribers:`, state.subject.subscribers);
710
+ break;
711
+ case `atom`:
712
+ case `writable_pure_selector`:
713
+ case `readonly_pure_selector`:
714
+ case `writable_held_selector`:
715
+ case `readonly_held_selector`: store.logger.info(`📢`, state.type, state.key, `went (`, update.oldValue, `->`, update.newValue, `) subscribers:`, state.subject.subscribers);
716
+ }
717
+ state.subject.next(update);
725
718
  };
726
719
 
727
720
  //#endregion
728
- //#region src/internal/selector/trace-selector-atoms.ts
729
- const traceSelectorAtoms = (store, directDependencyKey, covered) => {
730
- const rootKeys = [];
731
- const indirectDependencyKeys = getSelectorDependencyKeys(store, directDependencyKey);
732
- while (indirectDependencyKeys.length > 0) {
733
- const indirectDependencyKey = indirectDependencyKeys.shift();
734
- if (covered.has(indirectDependencyKey)) continue;
735
- covered.add(indirectDependencyKey);
736
- if (!isAtomKey(store, indirectDependencyKey)) indirectDependencyKeys.push(...getSelectorDependencyKeys(store, indirectDependencyKey));
737
- else if (!rootKeys.includes(indirectDependencyKey)) rootKeys.push(indirectDependencyKey);
738
- }
739
- return rootKeys;
740
- };
741
- const traceAllSelectorAtoms = (selector, store) => {
742
- const selectorKey = selector.key;
743
- const directDependencyKeys = getSelectorDependencyKeys(store, selectorKey);
744
- const covered = /* @__PURE__ */ new Set();
745
- return directDependencyKeys.flatMap((depKey) => isAtomKey(store, depKey) ? depKey : traceSelectorAtoms(store, depKey, covered)).map((atomKey) => store.atoms.get(atomKey));
721
+ //#region src/internal/set-state/set-atom.ts
722
+ const setAtom = (target, atom$1, next) => {
723
+ const oldValue = readOrComputeValue(target, atom$1);
724
+ let newValue = oldValue;
725
+ if (atom$1.type === `mutable_atom` && isChildStore(target)) {
726
+ const { parent } = target;
727
+ const copiedValue = copyMutableIfNeeded(target, atom$1, parent);
728
+ newValue = copiedValue;
729
+ }
730
+ newValue = become(next)(newValue);
731
+ target.logger.info(`📝`, `atom`, atom$1.key, `set to`, newValue);
732
+ newValue = cacheValue(target, atom$1.key, newValue, atom$1.subject);
733
+ markDone(target, atom$1.key);
734
+ evictDownStream(target, atom$1);
735
+ const update = {
736
+ oldValue,
737
+ newValue
738
+ };
739
+ if (!isChildStore(target)) {
740
+ emitUpdate(target, atom$1, update);
741
+ return;
742
+ }
743
+ if (target.on.transactionApplying.state === null) {
744
+ const { key } = atom$1;
745
+ if (isTransceiver(update.newValue)) return;
746
+ const atomUpdate = {
747
+ type: `atom_update`,
748
+ key,
749
+ ...update
750
+ };
751
+ if (atom$1.family) atomUpdate.family = atom$1.family;
752
+ target.transactionMeta.update.updates.push(atomUpdate);
753
+ target.logger.info(`📁`, `atom`, key, `stowed (`, update.oldValue, `->`, update.newValue, `)`);
754
+ } else if (atom$1.key.startsWith(`*`)) {
755
+ const mutableKey = atom$1.key.slice(1);
756
+ const mutableAtom = target.atoms.get(mutableKey);
757
+ let transceiver = target.valueMap.get(mutableKey);
758
+ if (mutableAtom.type === `mutable_atom` && isChildStore(target)) {
759
+ const { parent } = target;
760
+ const copiedValue = copyMutableIfNeeded(target, mutableAtom, parent);
761
+ transceiver = copiedValue;
762
+ }
763
+ const accepted = transceiver.do(update.newValue) === null;
764
+ if (accepted) evictDownStream(target, mutableAtom);
765
+ }
746
766
  };
747
767
 
748
768
  //#endregion
749
- //#region src/internal/selector/update-selector-atoms.ts
750
- const updateSelectorAtoms = (store, selectorType, selectorKey, dependency, covered) => {
751
- const target = newest(store);
752
- const { type: dependencyType, key: dependencyKey } = dependency;
753
- if (dependencyType === `atom` || dependencyType === `mutable_atom`) {
754
- target.selectorAtoms.set({
755
- selectorKey,
756
- atomKey: dependencyKey
757
- });
758
- store.logger.info(`🔍`, selectorType, selectorKey, `discovers root atom "${dependencyKey}"`);
769
+ //#region src/internal/set-state/reset-atom-or-selector.ts
770
+ function resetAtom(store, state) {
771
+ let def = state.default;
772
+ if (def instanceof Function) def = def();
773
+ setAtom(store, state, def);
774
+ }
775
+ function resetAtomOrSelector(store, state) {
776
+ switch (state.type) {
777
+ case `atom`:
778
+ case `mutable_atom`:
779
+ resetAtom(store, state);
780
+ break;
781
+ case `writable_pure_selector`:
782
+ case `writable_held_selector`:
783
+ {
784
+ const atoms = traceRootSelectorAtoms(store, state.key);
785
+ for (const atom$1 of atoms.values()) resetAtom(store, atom$1);
786
+ }
787
+ break;
788
+ }
789
+ }
790
+
791
+ //#endregion
792
+ //#region src/internal/families/get-family-of-token.ts
793
+ function getFamilyOfToken(store, token) {
794
+ if (token.family) {
795
+ const family = store.families.get(token.family.key);
796
+ if (family) return family;
797
+ }
798
+ }
799
+
800
+ //#endregion
801
+ //#region src/internal/set-state/reset-in-store.ts
802
+ function resetInStore(store, ...params) {
803
+ let token;
804
+ let family;
805
+ let key;
806
+ if (params.length === 1) {
807
+ token = params[0];
808
+ family = getFamilyOfToken(store, token) ?? null;
809
+ if (family) {
810
+ key = token.family ? parseJson(token.family.subKey) : null;
811
+ token = findInStore(store, family, key);
812
+ }
759
813
  } else {
760
- const rootKeys = traceSelectorAtoms(store, dependencyKey, covered);
761
- store.logger.info(`🔍`, selectorType, selectorKey, `discovers root atoms: [ ${rootKeys.map((key) => `"${key}"`).join(`, `)} ]`);
762
- for (const atomKey of rootKeys) target.selectorAtoms = target.selectorAtoms.set({
763
- selectorKey,
764
- atomKey
814
+ family = params[0];
815
+ key = params[1];
816
+ token = findInStore(store, family, key);
817
+ }
818
+ if (`counterfeit` in token && `family` in token) {
819
+ const subKey = token.family.subKey;
820
+ const disposal = store.disposalTraces.buffer.find((item) => item?.key === subKey);
821
+ store.logger.error(`❌`, token.type, token.key, `could not be reset because it was not found in the store "${store.config.name}".`, disposal ? `This state was previously disposed:\n${disposal.trace}` : `No previous disposal trace was found.`);
822
+ return;
823
+ }
824
+ const rejectionTime = openOperation(store, token);
825
+ if (rejectionTime) {
826
+ const unsubscribe = store.on.operationClose.subscribe(`waiting to reset "${token.key}" at T-${rejectionTime}`, () => {
827
+ unsubscribe();
828
+ store.logger.info(`🟢`, token.type, token.key, `resuming deferred resetState from T-${rejectionTime}`);
829
+ resetInStore(store, token);
765
830
  });
831
+ return;
832
+ }
833
+ const state = withdraw(store, token);
834
+ resetAtomOrSelector(store, state);
835
+ closeOperation(store);
836
+ }
837
+
838
+ //#endregion
839
+ //#region src/internal/set-state/set-atom-or-selector.ts
840
+ const setAtomOrSelector = (store, state, value) => {
841
+ switch (state.type) {
842
+ case `atom`:
843
+ case `mutable_atom`:
844
+ setAtom(store, state, value);
845
+ break;
846
+ case `writable_pure_selector`:
847
+ case `writable_held_selector`:
848
+ state.set(value);
849
+ break;
766
850
  }
767
- covered.add(dependencyKey);
768
851
  };
769
852
 
770
853
  //#endregion
771
- //#region src/internal/selector/register-selector.ts
772
- const registerSelector = (store, selectorType, selectorKey, covered) => ({
773
- get: (...params) => {
774
- const target = newest(store);
775
- let dependency;
854
+ //#region src/internal/set-state/set-into-store.ts
855
+ function setIntoStore(store, ...params) {
856
+ let token;
857
+ let family;
858
+ let key;
859
+ let value;
860
+ if (params.length === 2) {
861
+ token = params[0];
862
+ value = params[1];
863
+ family = getFamilyOfToken(store, token) ?? null;
864
+ if (family) {
865
+ key = token.family ? parseJson(token.family.subKey) : null;
866
+ token = findInStore(store, family, key);
867
+ }
868
+ } else {
869
+ family = params[0];
870
+ key = params[1];
871
+ value = params[2];
872
+ token = findInStore(store, family, key);
873
+ }
874
+ if (`counterfeit` in token && `family` in token) {
875
+ const subKey = token.family.subKey;
876
+ const disposal = store.disposalTraces.buffer.find((item) => item?.key === subKey);
877
+ store.logger.error(`❌`, token.type, token.key, `could not be set because it was not found in the store "${store.config.name}".`, disposal ? `This state was previously disposed:\n${disposal.trace}` : `No previous disposal trace was found.`);
878
+ return;
879
+ }
880
+ const rejectionTime = openOperation(store, token);
881
+ if (rejectionTime) {
882
+ const unsubscribe = store.on.operationClose.subscribe(`waiting to set "${token.key}" at T-${rejectionTime}`, () => {
883
+ unsubscribe();
884
+ store.logger.info(`🟢`, token.type, token.key, `resuming deferred setState from T-${rejectionTime}`);
885
+ setIntoStore(store, token, value);
886
+ });
887
+ return;
888
+ }
889
+ const state = withdraw(store, token);
890
+ setAtomOrSelector(store, state, value);
891
+ closeOperation(store);
892
+ }
893
+
894
+ //#endregion
895
+ //#region src/internal/keys.ts
896
+ const isAtomKey = (store, key) => newest(store).atoms.has(key);
897
+ const isSelectorKey = (store, key) => newest(store).writableSelectors.has(key);
898
+ const isReadonlySelectorKey = (store, key) => newest(store).readonlySelectors.has(key);
899
+ const isStateKey = (store, key) => isAtomKey(store, key) || isSelectorKey(store, key) || isReadonlySelectorKey(store, key);
900
+
901
+ //#endregion
902
+ //#region src/internal/selector/get-selector-dependency-keys.ts
903
+ const getSelectorDependencyKeys = (store, key) => {
904
+ const sources = newest(store).selectorGraph.getRelationEntries({ downstreamSelectorKey: key }).filter(([_, { source }]) => source !== key).map(([_, { source }]) => source).filter((source) => isStateKey(store, source));
905
+ return sources;
906
+ };
907
+
908
+ //#endregion
909
+ //#region src/internal/selector/trace-selector-atoms.ts
910
+ const traceRootSelectorAtoms = (store, selectorKey, covered = /* @__PURE__ */ new Set()) => {
911
+ const dependencies = getSelectorDependencyKeys(store, selectorKey);
912
+ const roots = /* @__PURE__ */ new Map();
913
+ while (dependencies.length > 0) {
914
+ const dependencyKey = dependencies.pop();
915
+ if (covered.has(dependencyKey)) continue;
916
+ covered.add(dependencyKey);
917
+ if (isAtomKey(store, dependencyKey)) {
918
+ const atom$1 = store.atoms.get(dependencyKey);
919
+ roots.set(atom$1.key, atom$1);
920
+ } else dependencies.push(...getSelectorDependencyKeys(store, dependencyKey));
921
+ }
922
+ return roots;
923
+ };
924
+
925
+ //#endregion
926
+ //#region src/internal/selector/update-selector-atoms.ts
927
+ const updateSelectorAtoms = (store, selectorType, selectorKey, dependency, covered) => {
928
+ const target = newest(store);
929
+ const { type: dependencyType, key: dependencyKey } = dependency;
930
+ if (dependencyType === `atom` || dependencyType === `mutable_atom`) {
931
+ target.selectorAtoms.set({
932
+ selectorKey,
933
+ atomKey: dependencyKey
934
+ });
935
+ store.logger.info(`🔍`, selectorType, selectorKey, `discovers root atom "${dependencyKey}"`);
936
+ } else {
937
+ const rootKeys = traceRootSelectorAtoms(store, dependencyKey, covered);
938
+ store.logger.info(`🔍`, selectorType, selectorKey, `discovers root atoms: [ ${[...rootKeys.values()].map((root) => `"${root.key}"`).join(`, `)} ]`);
939
+ for (const { key: atomKey } of rootKeys.values()) target.selectorAtoms = target.selectorAtoms.set({
940
+ selectorKey,
941
+ atomKey
942
+ });
943
+ }
944
+ covered.add(dependencyKey);
945
+ };
946
+
947
+ //#endregion
948
+ //#region src/internal/selector/register-selector.ts
949
+ const registerSelector = (store, selectorType, selectorKey, covered) => ({
950
+ get: (...params) => {
951
+ const target = newest(store);
952
+ let dependency;
776
953
  if (params.length === 2) {
777
954
  const [family, key] = params;
778
955
  dependency = findInStore(store, family, key);
@@ -818,6 +995,10 @@ const createReadonlyHeldSelector = (store, options, family) => {
818
995
  const type = `readonly_held_selector`;
819
996
  const { get, find, json } = registerSelector(target, type, key, covered);
820
997
  const getSelf = () => {
998
+ const innerTarget = newest(store);
999
+ const upstreamStates = innerTarget.selectorGraph.getRelationEntries({ downstreamSelectorKey: key });
1000
+ for (const [downstreamSelectorKey, { source }] of upstreamStates) if (source !== key) innerTarget.selectorGraph.delete(downstreamSelectorKey, key);
1001
+ innerTarget.selectorAtoms.delete(key);
821
1002
  options.get({
822
1003
  get,
823
1004
  find,
@@ -855,14 +1036,19 @@ const createReadonlyPureSelector = (store, options, family) => {
855
1036
  const type = `readonly_pure_selector`;
856
1037
  const { get, find, json } = registerSelector(target, type, key, covered);
857
1038
  const getSelf = () => {
1039
+ const innerTarget = newest(store);
1040
+ const upstreamStates = innerTarget.selectorGraph.getRelationEntries({ downstreamSelectorKey: key });
1041
+ for (const [downstreamSelectorKey, { source }] of upstreamStates) if (source !== key) innerTarget.selectorGraph.delete(downstreamSelectorKey, key);
1042
+ innerTarget.selectorAtoms.delete(key);
858
1043
  const value = options.get({
859
1044
  get,
860
1045
  find,
861
1046
  json
862
1047
  });
863
- cacheValue(newest(store), key, value, subject);
1048
+ const cached = cacheValue(innerTarget, key, value, subject);
1049
+ store.logger.info(`✨`, type, key, `=`, cached);
864
1050
  covered.clear();
865
- return value;
1051
+ return cached;
866
1052
  };
867
1053
  const readonlySelector = {
868
1054
  ...options,
@@ -873,8 +1059,6 @@ const createReadonlyPureSelector = (store, options, family) => {
873
1059
  ...family && { family }
874
1060
  };
875
1061
  target.readonlySelectors.set(key, readonlySelector);
876
- const initialValue = getSelf();
877
- store.logger.info(`✨`, type, key, `=`, initialValue);
878
1062
  const token = {
879
1063
  key,
880
1064
  type
@@ -884,639 +1068,66 @@ const createReadonlyPureSelector = (store, options, family) => {
884
1068
  };
885
1069
 
886
1070
  //#endregion
887
- //#region src/internal/selector/create-writable-held-selector.ts
888
- const createWritableHeldSelector = (store, options, family) => {
1071
+ //#region src/internal/transaction/abort-transaction.ts
1072
+ const abortTransaction = (store) => {
889
1073
  const target = newest(store);
890
- const subject = new Subject();
891
- const covered = /* @__PURE__ */ new Set();
892
- const { key, const: constant } = options;
893
- const type = `writable_held_selector`;
894
- const setterToolkit = registerSelector(target, type, key, covered);
895
- const { find, get, json } = setterToolkit;
896
- const getterToolkit = {
897
- find,
898
- get,
899
- json
900
- };
901
- const getSelf = (getFn = options.get, innerTarget = newest(store)) => {
902
- getFn(getterToolkit, constant);
903
- cacheValue(innerTarget, key, constant, subject);
904
- covered.clear();
905
- return constant;
906
- };
907
- const setSelf = (next) => {
908
- const innerTarget = newest(store);
909
- const oldValue = getSelf(options.get, innerTarget);
910
- const newValue = become(next)(oldValue);
911
- store.logger.info(`📝`, type, key, `set (`, oldValue, `->`, newValue, `)`);
912
- cacheValue(innerTarget, key, newValue, subject);
913
- markDone(innerTarget, key);
914
- if (isRootStore(innerTarget)) subject.next({
915
- newValue,
916
- oldValue
917
- });
918
- options.set(setterToolkit, newValue);
919
- };
920
- const mySelector = {
921
- ...options,
922
- type,
923
- subject,
924
- install: (s) => createWritableHeldSelector(s, options, family),
925
- get: getSelf,
926
- set: setSelf,
927
- ...family && { family }
928
- };
929
- target.writableSelectors.set(key, mySelector);
930
- const initialValue = getSelf();
931
- store.logger.info(`✨`, type, key, `=`, initialValue);
932
- const token = {
933
- key,
934
- type
935
- };
936
- if (family) token.family = family;
937
- return token;
1074
+ if (!isChildStore(target)) {
1075
+ store.logger.warn(`🐞`, `transaction`, `???`, `abortTransaction called outside of a transaction. This is probably a bug in AtomIO.`);
1076
+ return;
1077
+ }
1078
+ store.logger.info(`🪂`, `transaction`, target.transactionMeta.update.key, `Aborting transaction`);
1079
+ target.parent.child = null;
938
1080
  };
939
1081
 
940
1082
  //#endregion
941
- //#region src/internal/selector/create-writable-pure-selector.ts
942
- const createWritablePureSelector = (store, options, family) => {
943
- const target = newest(store);
944
- const subject = new Subject();
945
- const covered = /* @__PURE__ */ new Set();
946
- const key = options.key;
947
- const type = `writable_pure_selector`;
948
- const setterToolkit = registerSelector(target, type, key, covered);
949
- const { find, get, json } = setterToolkit;
950
- const getterToolkit = {
951
- find,
952
- get,
953
- json
954
- };
955
- const getSelf = (getFn = options.get, innerTarget = newest(store)) => {
956
- const value = getFn(getterToolkit);
957
- cacheValue(innerTarget, key, value, subject);
958
- covered.clear();
959
- return value;
960
- };
961
- const setSelf = (next) => {
962
- const innerTarget = newest(store);
963
- const oldValue = getSelf(options.get, innerTarget);
964
- const newValue = become(next)(oldValue);
965
- store.logger.info(`📝`, type, key, `set (`, oldValue, `->`, newValue, `)`);
966
- cacheValue(innerTarget, options.key, newValue, subject);
967
- markDone(innerTarget, options.key);
968
- if (isRootStore(innerTarget)) subject.next({
969
- newValue,
970
- oldValue
971
- });
972
- options.set(setterToolkit, newValue);
973
- };
974
- const mySelector = {
975
- ...options,
976
- type,
977
- subject,
978
- install: (s) => createWritablePureSelector(s, options, family),
979
- get: getSelf,
980
- set: setSelf,
981
- ...family && { family }
1083
+ //#region src/internal/capitalize.ts
1084
+ function capitalize(string) {
1085
+ return string[0].toUpperCase() + string.slice(1);
1086
+ }
1087
+
1088
+ //#endregion
1089
+ //#region src/internal/pretty-print.ts
1090
+ function prettyPrintTokenType(token) {
1091
+ return token.type.split(`_`).map(capitalize).join(` `);
1092
+ }
1093
+
1094
+ //#endregion
1095
+ //#region src/internal/not-found-error.ts
1096
+ var NotFoundError = class extends Error {
1097
+ constructor(token, store) {
1098
+ super(`${prettyPrintTokenType(token)} ${stringifyJson(token.key)} not found in store "${store.config.name}".`);
1099
+ }
1100
+ };
1101
+
1102
+ //#endregion
1103
+ //#region src/internal/transaction/act-upon-store.ts
1104
+ function actUponStore(store, token, id) {
1105
+ return (...parameters) => {
1106
+ const tx = withdraw(store, token);
1107
+ if (tx) return tx.run(parameters, id);
1108
+ throw new NotFoundError(token, store);
982
1109
  };
983
- target.writableSelectors.set(key, mySelector);
984
- const initialValue = getSelf();
985
- store.logger.info(`✨`, mySelector.type, mySelector.key, `=`, initialValue);
1110
+ }
1111
+
1112
+ //#endregion
1113
+ //#region src/internal/ingest-updates/ingest-atom-update.ts
1114
+ function ingestAtomUpdate(applying, atomUpdate, store) {
1115
+ const { key, newValue, oldValue } = atomUpdate;
1116
+ const value = applying === `newValue` ? newValue : oldValue;
986
1117
  const token = {
987
1118
  key,
988
- type
1119
+ type: `atom`
989
1120
  };
990
- if (family) token.family = family;
991
- return token;
992
- };
1121
+ if (atomUpdate.family) Object.assign(token, { family: atomUpdate.family });
1122
+ setIntoStore(store, token, value);
1123
+ }
993
1124
 
994
1125
  //#endregion
995
- //#region src/internal/selector/create-standalone-selector.ts
996
- function createStandaloneSelector(store, options) {
997
- const isWritable = `set` in options;
998
- const isHeld = `const` in options;
999
- if (isHeld && isWritable) {
1000
- const state$1 = createWritableHeldSelector(store, options, void 0);
1001
- store.on.selectorCreation.next(state$1);
1002
- return state$1;
1003
- }
1004
- if (isHeld) {
1005
- const state$1 = createReadonlyHeldSelector(store, options, void 0);
1006
- store.on.selectorCreation.next(state$1);
1007
- return state$1;
1008
- }
1009
- if (isWritable) {
1010
- const state$1 = createWritablePureSelector(store, options, void 0);
1011
- store.on.selectorCreation.next(state$1);
1012
- return state$1;
1013
- }
1014
- const state = createReadonlyPureSelector(store, options, void 0);
1015
- store.on.selectorCreation.next(state);
1016
- return state;
1017
- }
1018
-
1019
- //#endregion
1020
- //#region src/internal/selector/dispose-selector.ts
1021
- function disposeSelector(store, selectorToken) {
1022
- const target = newest(store);
1023
- const { key, type } = selectorToken;
1024
- const selector = withdraw(target, selectorToken);
1025
- if (!selector.family) store.logger.error(`❌`, type, key, `Standalone selectors cannot be disposed.`);
1026
- else {
1027
- const molecule = target.molecules.get(selector.family.subKey);
1028
- if (molecule) target.moleculeData.delete(selector.family.subKey, selector.family.key);
1029
- let familyToken;
1030
- switch (selectorToken.type) {
1031
- case `writable_held_selector`:
1032
- {
1033
- target.writableSelectors.delete(key);
1034
- familyToken = {
1035
- key: selector.family.key,
1036
- type: `writable_held_selector_family`
1037
- };
1038
- const family = withdraw(store, familyToken);
1039
- family.subject.next({
1040
- type: `state_disposal`,
1041
- subType: `selector`,
1042
- token: selectorToken
1043
- });
1044
- }
1045
- break;
1046
- case `writable_pure_selector`:
1047
- {
1048
- target.writableSelectors.delete(key);
1049
- familyToken = {
1050
- key: selector.family.key,
1051
- type: `writable_pure_selector_family`
1052
- };
1053
- const family = withdraw(store, familyToken);
1054
- family.subject.next({
1055
- type: `state_disposal`,
1056
- subType: `selector`,
1057
- token: selectorToken
1058
- });
1059
- }
1060
- break;
1061
- case `readonly_held_selector`:
1062
- {
1063
- target.readonlySelectors.delete(key);
1064
- familyToken = {
1065
- key: selector.family.key,
1066
- type: `readonly_held_selector_family`
1067
- };
1068
- const family = withdraw(store, familyToken);
1069
- family.subject.next({
1070
- type: `state_disposal`,
1071
- subType: `selector`,
1072
- token: selectorToken
1073
- });
1074
- }
1075
- break;
1076
- case `readonly_pure_selector`:
1077
- {
1078
- target.readonlySelectors.delete(key);
1079
- familyToken = {
1080
- key: selector.family.key,
1081
- type: `readonly_pure_selector_family`
1082
- };
1083
- const family = withdraw(store, familyToken);
1084
- family.subject.next({
1085
- type: `state_disposal`,
1086
- subType: `selector`,
1087
- token: selectorToken
1088
- });
1089
- }
1090
- break;
1091
- }
1092
- target.valueMap.delete(key);
1093
- target.selectorAtoms.delete(key);
1094
- target.selectorGraph.delete(key);
1095
- store.logger.info(`🔥`, selectorToken.type, key, `deleted`);
1096
- if (isChildStore(target) && target.transactionMeta.phase === `building`) target.transactionMeta.update.updates.push({
1097
- type: `state_disposal`,
1098
- subType: `selector`,
1099
- token: selectorToken
1100
- });
1101
- else store.on.selectorDisposal.next(selectorToken);
1102
- }
1103
- }
1104
-
1105
- //#endregion
1106
- //#region src/internal/families/create-readonly-pure-selector-family.ts
1107
- function createReadonlyPureSelectorFamily(store, options, internalRoles) {
1108
- const familyKey = options.key;
1109
- const type = `readonly_pure_selector_family`;
1110
- const familyToken = {
1111
- key: familyKey,
1112
- type
1113
- };
1114
- const existing = store.families.get(familyKey);
1115
- if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1116
- const subject = new Subject();
1117
- const familyFunction = (key) => {
1118
- const subKey = stringifyJson(key);
1119
- const family = {
1120
- key: familyKey,
1121
- subKey
1122
- };
1123
- const fullKey = `${familyKey}(${subKey})`;
1124
- const target = newest(store);
1125
- const token = createReadonlyPureSelector(target, {
1126
- key: fullKey,
1127
- get: options.get(key)
1128
- }, family);
1129
- subject.next({
1130
- type: `state_creation`,
1131
- token
1132
- });
1133
- return token;
1134
- };
1135
- const readonlySelectorFamily = Object.assign(familyFunction, familyToken, {
1136
- internalRoles,
1137
- subject,
1138
- install: (s) => createReadonlyPureSelectorFamily(s, options),
1139
- default: (key) => {
1140
- const getFn = options.get(key);
1141
- return getFn({
1142
- get: ((...args) => getFromStore(store, ...args)),
1143
- find: ((...args) => findInStore(store, ...args)),
1144
- json: (token) => getJsonToken(store, token)
1145
- });
1146
- }
1147
- });
1148
- store.families.set(familyKey, readonlySelectorFamily);
1149
- return familyToken;
1150
- }
1151
-
1152
- //#endregion
1153
- //#region src/internal/families/create-readonly-held-selector-family.ts
1154
- function createReadonlyHeldSelectorFamily(store, options, internalRoles) {
1155
- const familyKey = options.key;
1156
- const type = `readonly_held_selector_family`;
1157
- const familyToken = {
1158
- key: familyKey,
1159
- type
1160
- };
1161
- const existing = store.families.get(familyKey);
1162
- if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1163
- const subject = new Subject();
1164
- const familyFunction = (key) => {
1165
- const subKey = stringifyJson(key);
1166
- const family = {
1167
- key: familyKey,
1168
- subKey
1169
- };
1170
- const fullKey = `${familyKey}(${subKey})`;
1171
- const target = newest(store);
1172
- const token = createReadonlyHeldSelector(target, {
1173
- key: fullKey,
1174
- const: options.const(key),
1175
- get: options.get(key)
1176
- }, family);
1177
- subject.next({
1178
- type: `state_creation`,
1179
- token
1180
- });
1181
- return token;
1182
- };
1183
- const readonlySelectorFamily = Object.assign(familyFunction, familyToken, {
1184
- internalRoles,
1185
- subject,
1186
- install: (s) => createReadonlyHeldSelectorFamily(s, options),
1187
- default: options.const
1188
- });
1189
- store.families.set(familyKey, readonlySelectorFamily);
1190
- return familyToken;
1191
- }
1192
-
1193
- //#endregion
1194
- //#region src/internal/families/create-writable-held-selector-family.ts
1195
- function createWritableHeldSelectorFamily(store, options, internalRoles) {
1196
- const familyKey = options.key;
1197
- const type = `writable_held_selector_family`;
1198
- const familyToken = {
1199
- key: familyKey,
1200
- type
1201
- };
1202
- const existing = store.families.get(familyKey);
1203
- if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1204
- const subject = new Subject();
1205
- const familyFunction = (key) => {
1206
- const subKey = stringifyJson(key);
1207
- const family = {
1208
- key: familyKey,
1209
- subKey
1210
- };
1211
- const fullKey = `${familyKey}(${subKey})`;
1212
- const target = newest(store);
1213
- const token = createWritableHeldSelector(target, {
1214
- key: fullKey,
1215
- const: options.const(key),
1216
- get: options.get(key),
1217
- set: options.set(key)
1218
- }, family);
1219
- subject.next({
1220
- type: `state_creation`,
1221
- token
1222
- });
1223
- return token;
1224
- };
1225
- const selectorFamily$1 = Object.assign(familyFunction, familyToken, {
1226
- internalRoles,
1227
- subject,
1228
- install: (s) => createWritableHeldSelectorFamily(s, options),
1229
- default: options.const
1230
- });
1231
- store.families.set(familyKey, selectorFamily$1);
1232
- return familyToken;
1233
- }
1234
-
1235
- //#endregion
1236
- //#region src/internal/families/create-writable-pure-selector-family.ts
1237
- function createWritablePureSelectorFamily(store, options, internalRoles) {
1238
- const familyKey = options.key;
1239
- const type = `writable_pure_selector_family`;
1240
- const familyToken = {
1241
- key: familyKey,
1242
- type
1243
- };
1244
- const existing = store.families.get(familyKey);
1245
- if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1246
- const subject = new Subject();
1247
- const familyFunction = (key) => {
1248
- const subKey = stringifyJson(key);
1249
- const family = {
1250
- key: familyKey,
1251
- subKey
1252
- };
1253
- const fullKey = `${familyKey}(${subKey})`;
1254
- const target = newest(store);
1255
- const token = createWritablePureSelector(target, {
1256
- key: fullKey,
1257
- get: options.get(key),
1258
- set: options.set(key)
1259
- }, family);
1260
- subject.next({
1261
- type: `state_creation`,
1262
- token
1263
- });
1264
- return token;
1265
- };
1266
- const selectorFamily$1 = Object.assign(familyFunction, familyToken, {
1267
- internalRoles,
1268
- subject,
1269
- install: (s) => createWritablePureSelectorFamily(s, options),
1270
- default: (key) => {
1271
- const getFn = options.get(key);
1272
- return getFn({
1273
- get: ((...args) => getFromStore(store, ...args)),
1274
- find: ((...args) => findInStore(store, ...args)),
1275
- json: (token) => getJsonToken(store, token)
1276
- });
1277
- }
1278
- });
1279
- store.families.set(familyKey, selectorFamily$1);
1280
- return familyToken;
1281
- }
1282
-
1283
- //#endregion
1284
- //#region src/internal/families/create-selector-family.ts
1285
- function createSelectorFamily(store, options) {
1286
- const isWritable = `set` in options;
1287
- const isHeld = `const` in options;
1288
- if (isHeld && isWritable) return createWritableHeldSelectorFamily(store, options, void 0);
1289
- if (isHeld) return createReadonlyHeldSelectorFamily(store, options, void 0);
1290
- if (isWritable) return createWritablePureSelectorFamily(store, options);
1291
- return createReadonlyPureSelectorFamily(store, options);
1292
- }
1293
-
1294
- //#endregion
1295
- //#region src/internal/families/init-family-member.ts
1296
- function initFamilyMemberInStore(store, token, key) {
1297
- const family = store.families.get(token.key);
1298
- if (family === void 0) throw new NotFoundError(token, store);
1299
- const state = family(key);
1300
- const target = newest(store);
1301
- if (state.family) {
1302
- if (isRootStore(target)) switch (state.type) {
1303
- case `atom`:
1304
- case `mutable_atom`:
1305
- store.on.atomCreation.next(state);
1306
- break;
1307
- case `writable_pure_selector`:
1308
- case `readonly_pure_selector`:
1309
- case `writable_held_selector`:
1310
- case `readonly_held_selector`:
1311
- store.on.selectorCreation.next(state);
1312
- break;
1313
- }
1314
- else if (isChildStore(target) && target.on.transactionApplying.state === null) target.transactionMeta.update.updates.push({
1315
- type: `state_creation`,
1316
- token: state
1317
- });
1318
- }
1319
- return state;
1320
- }
1321
-
1322
- //#endregion
1323
- //#region src/internal/families/seek-in-store.ts
1324
- function seekInStore(store, token, key) {
1325
- const subKey = stringifyJson(key);
1326
- const fullKey = `${token.key}(${subKey})`;
1327
- const target = newest(store);
1328
- let state;
1329
- switch (token.type) {
1330
- case `atom_family`:
1331
- case `mutable_atom_family`:
1332
- state = target.atoms.get(fullKey);
1333
- break;
1334
- case `writable_held_selector_family`:
1335
- case `writable_pure_selector_family`:
1336
- state = target.writableSelectors.get(fullKey);
1337
- break;
1338
- case `readonly_held_selector_family`:
1339
- case `readonly_pure_selector_family`:
1340
- state = target.readonlySelectors.get(fullKey);
1341
- break;
1342
- }
1343
- if (state) return deposit(state);
1344
- return state;
1345
- }
1346
-
1347
- //#endregion
1348
- //#region src/internal/families/find-in-store.ts
1349
- function findInStore(store, token, key) {
1350
- let state = seekInStore(store, token, key);
1351
- if (state) return state;
1352
- const stringKey = stringifyJson(key);
1353
- const molecule = store.molecules.get(stringKey);
1354
- if (!molecule && store.config.lifespan === `immortal`) {
1355
- const fakeToken = counterfeit(token, key);
1356
- store.logger.error(`❌`, fakeToken.type, fakeToken.key, `was not found in store "${store.config.name}"; returned a counterfeit token.`);
1357
- return fakeToken;
1358
- }
1359
- state = initFamilyMemberInStore(store, token, key);
1360
- if (molecule) {
1361
- const target = newest(store);
1362
- target.moleculeData.set(stringKey, token.key);
1363
- }
1364
- return state;
1365
- }
1366
-
1367
- //#endregion
1368
- //#region src/internal/families/dispose-from-store.ts
1369
- function disposeFromStore(store, ...params) {
1370
- let token;
1371
- if (params.length === 1) token = params[0];
1372
- else {
1373
- const family = params[0];
1374
- const key = params[1];
1375
- const maybeToken = findInStore(store, family, key);
1376
- token = maybeToken;
1377
- }
1378
- try {
1379
- withdraw(store, token);
1380
- } catch (_) {
1381
- store.logger.error(`❌`, token.type, token.key, `could not be disposed because it was not found in the store "${store.config.name}".`);
1382
- return;
1383
- }
1384
- switch (token.type) {
1385
- case `atom`:
1386
- case `mutable_atom`:
1387
- disposeAtom(store, token);
1388
- break;
1389
- case `writable_pure_selector`:
1390
- case `readonly_pure_selector`:
1391
- case `writable_held_selector`:
1392
- case `readonly_held_selector`:
1393
- disposeSelector(store, token);
1394
- break;
1395
- }
1396
- }
1397
-
1398
- //#endregion
1399
- //#region src/internal/families/get-family-of-token.ts
1400
- function getFamilyOfToken(store, token) {
1401
- if (token.family) {
1402
- const family = store.families.get(token.family.key);
1403
- if (family) return family;
1404
- }
1405
- }
1406
-
1407
- //#endregion
1408
- //#region src/internal/set-state/reset-in-store.ts
1409
- function resetInStore(store, ...params) {
1410
- let token;
1411
- let family;
1412
- let key;
1413
- if (params.length === 1) {
1414
- token = params[0];
1415
- family = getFamilyOfToken(store, token) ?? null;
1416
- if (family) {
1417
- key = token.family ? parseJson(token.family.subKey) : null;
1418
- token = findInStore(store, family, key);
1419
- }
1420
- } else {
1421
- family = params[0];
1422
- key = params[1];
1423
- token = findInStore(store, family, key);
1424
- }
1425
- if (`counterfeit` in token && `family` in token) {
1426
- const subKey = token.family.subKey;
1427
- const disposal = store.disposalTraces.buffer.find((item) => item?.key === subKey);
1428
- store.logger.error(`❌`, token.type, token.key, `could not be reset because it was not found in the store "${store.config.name}".`, disposal ? `This state was previously disposed:\n${disposal.trace}` : `No previous disposal trace was found.`);
1429
- return;
1430
- }
1431
- const rejectionTime = openOperation(store, token);
1432
- if (rejectionTime) {
1433
- const unsubscribe = store.on.operationClose.subscribe(`waiting to reset "${token.key}" at T-${rejectionTime}`, () => {
1434
- unsubscribe();
1435
- store.logger.info(`🟢`, token.type, token.key, `resuming deferred resetState from T-${rejectionTime}`);
1436
- resetInStore(store, token);
1437
- });
1438
- return;
1439
- }
1440
- const state = withdraw(store, token);
1441
- resetAtomOrSelector(store, state);
1442
- closeOperation(store);
1443
- }
1444
-
1445
- //#endregion
1446
- //#region src/internal/set-state/set-atom-or-selector.ts
1447
- const setAtomOrSelector = (store, state, value) => {
1448
- switch (state.type) {
1449
- case `atom`:
1450
- case `mutable_atom`:
1451
- setAtom(store, state, value);
1452
- break;
1453
- case `writable_pure_selector`:
1454
- case `writable_held_selector`:
1455
- state.set(value);
1456
- break;
1457
- }
1458
- };
1459
-
1460
- //#endregion
1461
- //#region src/internal/set-state/set-into-store.ts
1462
- function setIntoStore(store, ...params) {
1463
- let token;
1464
- let family;
1465
- let key;
1466
- let value;
1467
- if (params.length === 2) {
1468
- token = params[0];
1469
- value = params[1];
1470
- family = getFamilyOfToken(store, token) ?? null;
1471
- if (family) {
1472
- key = token.family ? parseJson(token.family.subKey) : null;
1473
- token = findInStore(store, family, key);
1474
- }
1475
- } else {
1476
- family = params[0];
1477
- key = params[1];
1478
- value = params[2];
1479
- token = findInStore(store, family, key);
1480
- }
1481
- if (`counterfeit` in token && `family` in token) {
1482
- const subKey = token.family.subKey;
1483
- const disposal = store.disposalTraces.buffer.find((item) => item?.key === subKey);
1484
- store.logger.error(`❌`, token.type, token.key, `could not be set because it was not found in the store "${store.config.name}".`, disposal ? `This state was previously disposed:\n${disposal.trace}` : `No previous disposal trace was found.`);
1485
- return;
1486
- }
1487
- const rejectionTime = openOperation(store, token);
1488
- if (rejectionTime) {
1489
- const unsubscribe = store.on.operationClose.subscribe(`waiting to set "${token.key}" at T-${rejectionTime}`, () => {
1490
- unsubscribe();
1491
- store.logger.info(`🟢`, token.type, token.key, `resuming deferred setState from T-${rejectionTime}`);
1492
- setIntoStore(store, token, value);
1493
- });
1494
- return;
1495
- }
1496
- const state = withdraw(store, token);
1497
- setAtomOrSelector(store, state, value);
1498
- closeOperation(store);
1499
- }
1500
-
1501
- //#endregion
1502
- //#region src/internal/ingest-updates/ingest-atom-update.ts
1503
- function ingestAtomUpdate(applying, atomUpdate, store) {
1504
- const { key, newValue, oldValue } = atomUpdate;
1505
- const value = applying === `newValue` ? newValue : oldValue;
1506
- const token = {
1507
- key,
1508
- type: `atom`
1509
- };
1510
- if (atomUpdate.family) Object.assign(token, { family: atomUpdate.family });
1511
- setIntoStore(store, token, value);
1512
- }
1513
-
1514
- //#endregion
1515
- //#region src/internal/get-trace.ts
1516
- function getTrace(error) {
1517
- const { stack } = error;
1518
- if (stack) return `\n` + stack.split(`\n`)?.slice(1)?.join(`\n`);
1519
- return ``;
1126
+ //#region src/internal/get-trace.ts
1127
+ function getTrace(error) {
1128
+ const { stack } = error;
1129
+ if (stack) return `\n` + stack.split(`\n`)?.slice(1)?.join(`\n`);
1130
+ return ``;
1520
1131
  }
1521
1132
 
1522
1133
  //#endregion
@@ -1817,72 +1428,38 @@ const applyTransaction = (output, store) => {
1817
1428
  return;
1818
1429
  }
1819
1430
  child.transactionMeta.phase = `applying`;
1820
- child.transactionMeta.update.output = output;
1821
- parent.child = null;
1822
- parent.on.transactionApplying.next(child.transactionMeta);
1823
- const { updates } = child.transactionMeta.update;
1824
- store.logger.info(`🛄`, `transaction`, child.transactionMeta.update.key, `Applying transaction with ${updates.length} updates:`, updates);
1825
- ingestTransactionUpdate(`newValue`, child.transactionMeta.update, parent);
1826
- if (isRootStore(parent)) {
1827
- setEpochNumberOfAction(parent, child.transactionMeta.update.key, child.transactionMeta.update.epoch);
1828
- const myTransaction = withdraw(store, {
1829
- key: child.transactionMeta.update.key,
1830
- type: `transaction`
1831
- });
1832
- myTransaction?.subject.next(child.transactionMeta.update);
1833
- store.logger.info(`🛬`, `transaction`, child.transactionMeta.update.key, `Finished applying transaction.`);
1834
- } else if (isChildStore(parent)) parent.transactionMeta.update.updates.push(child.transactionMeta.update);
1835
- parent.on.transactionApplying.next(null);
1836
- };
1837
-
1838
- //#endregion
1839
- //#region src/internal/transaction/assign-transaction-to-continuity.ts
1840
- function assignTransactionToContinuity(store, continuityKey, transactionKey) {
1841
- const isRoot = isRootStore(store);
1842
- if (!isRoot) return;
1843
- const { epoch, actionContinuities } = store.transactionMeta;
1844
- actionContinuities.set(continuityKey, transactionKey);
1845
- if (!epoch.has(continuityKey)) epoch.set(continuityKey, -1);
1846
- }
1847
-
1848
- //#endregion
1849
- //#region src/internal/get-environment-data.ts
1850
- function getEnvironmentData(store) {
1851
- return { store };
1852
- }
1853
-
1854
- //#endregion
1855
- //#region src/internal/get-state/get-from-store.ts
1856
- function getFromStore(store, ...params) {
1857
- let token;
1858
- let family;
1859
- let key;
1860
- if (params.length === 1) token = params[0];
1861
- else {
1862
- family = params[0];
1863
- key = params[1];
1864
- token = findInStore(store, family, key);
1865
- }
1866
- if (`counterfeit` in token && `family` in token) {
1867
- family = store.families.get(token.family.key);
1868
- const subKey = token.family.subKey;
1869
- const disposal = store.disposalTraces.buffer.find((item) => item?.key === subKey);
1870
- store.logger.error(`❌`, token.type, token.key, `could not be retrieved because it was not found in the store "${store.config.name}".`, disposal ? `This state was previously disposed:\n${disposal.trace}` : `No previous disposal trace was found.`);
1871
- switch (family.type) {
1872
- case `atom_family`:
1873
- case `mutable_atom_family`: return store.defaults.get(family.key);
1874
- case `readonly_pure_selector_family`:
1875
- case `writable_pure_selector_family`:
1876
- case `readonly_held_selector_family`:
1877
- case `writable_held_selector_family`: {
1878
- if (store.defaults.has(family.key)) return store.defaults.get(token.family.key);
1879
- const defaultValue = withdraw(store, family).default(subKey);
1880
- store.defaults.set(family.key, defaultValue);
1881
- return defaultValue;
1882
- }
1883
- }
1884
- }
1885
- return readOrComputeValue(store, withdraw(store, token));
1431
+ child.transactionMeta.update.output = output;
1432
+ parent.child = null;
1433
+ parent.on.transactionApplying.next(child.transactionMeta);
1434
+ const { updates } = child.transactionMeta.update;
1435
+ store.logger.info(`🛄`, `transaction`, child.transactionMeta.update.key, `Applying transaction with ${updates.length} updates:`, updates);
1436
+ ingestTransactionUpdate(`newValue`, child.transactionMeta.update, parent);
1437
+ if (isRootStore(parent)) {
1438
+ setEpochNumberOfAction(parent, child.transactionMeta.update.key, child.transactionMeta.update.epoch);
1439
+ const myTransaction = withdraw(store, {
1440
+ key: child.transactionMeta.update.key,
1441
+ type: `transaction`
1442
+ });
1443
+ myTransaction?.subject.next(child.transactionMeta.update);
1444
+ store.logger.info(`🛬`, `transaction`, child.transactionMeta.update.key, `Finished applying transaction.`);
1445
+ } else if (isChildStore(parent)) parent.transactionMeta.update.updates.push(child.transactionMeta.update);
1446
+ parent.on.transactionApplying.next(null);
1447
+ };
1448
+
1449
+ //#endregion
1450
+ //#region src/internal/transaction/assign-transaction-to-continuity.ts
1451
+ function assignTransactionToContinuity(store, continuityKey, transactionKey) {
1452
+ const isRoot = isRootStore(store);
1453
+ if (!isRoot) return;
1454
+ const { epoch, actionContinuities } = store.transactionMeta;
1455
+ actionContinuities.set(continuityKey, transactionKey);
1456
+ if (!epoch.has(continuityKey)) epoch.set(continuityKey, -1);
1457
+ }
1458
+
1459
+ //#endregion
1460
+ //#region src/internal/get-environment-data.ts
1461
+ function getEnvironmentData(store) {
1462
+ return { store };
1886
1463
  }
1887
1464
 
1888
1465
  //#endregion
@@ -1980,265 +1557,605 @@ const buildTransaction = (store, key, params, id) => {
1980
1557
  }),
1981
1558
  env: () => getEnvironmentData(child)
1982
1559
  }
1983
- };
1984
- const child = Object.assign(childBase, { transactionMeta });
1985
- parent.child = child;
1986
- store.logger.info(`🛫`, `transaction`, key, `Building transaction with params:`, params);
1987
- return child;
1988
- };
1560
+ };
1561
+ const child = Object.assign(childBase, { transactionMeta });
1562
+ parent.child = child;
1563
+ store.logger.info(`🛫`, `transaction`, key, `Building transaction with params:`, params);
1564
+ return child;
1565
+ };
1566
+
1567
+ //#endregion
1568
+ //#region src/internal/transaction/create-transaction.ts
1569
+ function createTransaction(store, options) {
1570
+ const { key } = options;
1571
+ const transactionAlreadyExists = store.transactions.has(key);
1572
+ const newTransaction = {
1573
+ key,
1574
+ type: `transaction`,
1575
+ run: (params, id) => {
1576
+ const childStore = buildTransaction(store, key, params, id);
1577
+ try {
1578
+ const target$1 = newest(store);
1579
+ const { toolkit } = childStore.transactionMeta;
1580
+ const output = options.do(toolkit, ...params);
1581
+ applyTransaction(output, target$1);
1582
+ return output;
1583
+ } catch (thrown) {
1584
+ abortTransaction(target);
1585
+ store.logger.warn(`💥`, `transaction`, key, `caught:`, thrown);
1586
+ throw thrown;
1587
+ }
1588
+ },
1589
+ install: (s) => createTransaction(s, options),
1590
+ subject: new Subject()
1591
+ };
1592
+ const target = newest(store);
1593
+ target.transactions.set(key, newTransaction);
1594
+ const token = deposit(newTransaction);
1595
+ if (!transactionAlreadyExists) store.on.transactionCreation.next(token);
1596
+ return token;
1597
+ }
1598
+
1599
+ //#endregion
1600
+ //#region src/internal/transaction/index.ts
1601
+ const TRANSACTION_PHASES = [
1602
+ `idle`,
1603
+ `building`,
1604
+ `applying`
1605
+ ];
1606
+
1607
+ //#endregion
1608
+ //#region src/internal/selector/create-writable-held-selector.ts
1609
+ const createWritableHeldSelector = (store, options, family) => {
1610
+ const target = newest(store);
1611
+ const subject = new Subject();
1612
+ const covered = /* @__PURE__ */ new Set();
1613
+ const { key, const: constant } = options;
1614
+ const type = `writable_held_selector`;
1615
+ const setterToolkit = registerSelector(target, type, key, covered);
1616
+ const { find, get, json } = setterToolkit;
1617
+ const getterToolkit = {
1618
+ find,
1619
+ get,
1620
+ json
1621
+ };
1622
+ const getSelf = (getFn = options.get, innerTarget = newest(store)) => {
1623
+ const upstreamStates = innerTarget.selectorGraph.getRelationEntries({ downstreamSelectorKey: key });
1624
+ for (const [downstreamSelectorKey, { source }] of upstreamStates) if (source !== key) innerTarget.selectorGraph.delete(downstreamSelectorKey, key);
1625
+ innerTarget.selectorAtoms.delete(key);
1626
+ getFn(getterToolkit, constant);
1627
+ cacheValue(innerTarget, key, constant, subject);
1628
+ store.logger.info(`✨`, type, key, `=`, constant);
1629
+ covered.clear();
1630
+ return constant;
1631
+ };
1632
+ const setSelf = (next) => {
1633
+ const innerTarget = newest(store);
1634
+ const oldValue = getSelf(options.get, innerTarget);
1635
+ const newValue = become(next)(oldValue);
1636
+ store.logger.info(`📝`, type, key, `set (`, oldValue, `->`, newValue, `)`);
1637
+ cacheValue(innerTarget, key, newValue, subject);
1638
+ markDone(innerTarget, key);
1639
+ if (isRootStore(innerTarget)) subject.next({
1640
+ newValue,
1641
+ oldValue
1642
+ });
1643
+ options.set(setterToolkit, newValue);
1644
+ };
1645
+ const mySelector = {
1646
+ ...options,
1647
+ type,
1648
+ subject,
1649
+ install: (s) => createWritableHeldSelector(s, options, family),
1650
+ get: getSelf,
1651
+ set: setSelf,
1652
+ ...family && { family }
1653
+ };
1654
+ target.writableSelectors.set(key, mySelector);
1655
+ const token = {
1656
+ key,
1657
+ type
1658
+ };
1659
+ if (family) token.family = family;
1660
+ return token;
1661
+ };
1662
+
1663
+ //#endregion
1664
+ //#region src/internal/selector/create-writable-pure-selector.ts
1665
+ const createWritablePureSelector = (store, options, family) => {
1666
+ const target = newest(store);
1667
+ const subject = new Subject();
1668
+ const covered = /* @__PURE__ */ new Set();
1669
+ const key = options.key;
1670
+ const type = `writable_pure_selector`;
1671
+ const setterToolkit = registerSelector(target, type, key, covered);
1672
+ const { find, get, json } = setterToolkit;
1673
+ const getterToolkit = {
1674
+ find,
1675
+ get,
1676
+ json
1677
+ };
1678
+ const getSelf = (getFn = options.get, innerTarget = newest(store)) => {
1679
+ const upstreamStates = innerTarget.selectorGraph.getRelationEntries({ downstreamSelectorKey: key });
1680
+ for (const [downstreamSelectorKey, { source }] of upstreamStates) if (source !== key) innerTarget.selectorGraph.delete(downstreamSelectorKey, key);
1681
+ innerTarget.selectorAtoms.delete(key);
1682
+ const value = getFn(getterToolkit);
1683
+ const cached = cacheValue(innerTarget, key, value, subject);
1684
+ store.logger.info(`✨`, type, key, `=`, cached);
1685
+ covered.clear();
1686
+ return value;
1687
+ };
1688
+ const setSelf = (next) => {
1689
+ const innerTarget = newest(store);
1690
+ const oldValue = getSelf(options.get, innerTarget);
1691
+ const newValue = become(next)(oldValue);
1692
+ store.logger.info(`📝`, type, key, `set (`, oldValue, `->`, newValue, `)`);
1693
+ cacheValue(innerTarget, options.key, newValue, subject);
1694
+ markDone(innerTarget, options.key);
1695
+ if (isRootStore(innerTarget)) subject.next({
1696
+ newValue,
1697
+ oldValue
1698
+ });
1699
+ options.set(setterToolkit, newValue);
1700
+ };
1701
+ const mySelector = {
1702
+ ...options,
1703
+ type,
1704
+ subject,
1705
+ install: (s) => createWritablePureSelector(s, options, family),
1706
+ get: getSelf,
1707
+ set: setSelf,
1708
+ ...family && { family }
1709
+ };
1710
+ target.writableSelectors.set(key, mySelector);
1711
+ const initialValue = getSelf();
1712
+ store.logger.info(`✨`, mySelector.type, mySelector.key, `=`, initialValue);
1713
+ const token = {
1714
+ key,
1715
+ type
1716
+ };
1717
+ if (family) token.family = family;
1718
+ return token;
1719
+ };
1720
+
1721
+ //#endregion
1722
+ //#region src/internal/selector/create-standalone-selector.ts
1723
+ function createStandaloneSelector(store, options) {
1724
+ const isWritable = `set` in options;
1725
+ const isHeld = `const` in options;
1726
+ if (isHeld && isWritable) {
1727
+ const state$1 = createWritableHeldSelector(store, options, void 0);
1728
+ store.on.selectorCreation.next(state$1);
1729
+ return state$1;
1730
+ }
1731
+ if (isHeld) {
1732
+ const state$1 = createReadonlyHeldSelector(store, options, void 0);
1733
+ store.on.selectorCreation.next(state$1);
1734
+ return state$1;
1735
+ }
1736
+ if (isWritable) {
1737
+ const state$1 = createWritablePureSelector(store, options, void 0);
1738
+ store.on.selectorCreation.next(state$1);
1739
+ return state$1;
1740
+ }
1741
+ const state = createReadonlyPureSelector(store, options, void 0);
1742
+ store.on.selectorCreation.next(state);
1743
+ return state;
1744
+ }
1745
+
1746
+ //#endregion
1747
+ //#region src/internal/selector/dispose-selector.ts
1748
+ function disposeSelector(store, selectorToken) {
1749
+ const target = newest(store);
1750
+ const { key, type } = selectorToken;
1751
+ const selector = withdraw(target, selectorToken);
1752
+ if (!selector.family) store.logger.error(`❌`, type, key, `Standalone selectors cannot be disposed.`);
1753
+ else {
1754
+ const molecule = target.molecules.get(selector.family.subKey);
1755
+ if (molecule) target.moleculeData.delete(selector.family.subKey, selector.family.key);
1756
+ let familyToken;
1757
+ switch (selectorToken.type) {
1758
+ case `writable_held_selector`:
1759
+ {
1760
+ target.writableSelectors.delete(key);
1761
+ familyToken = {
1762
+ key: selector.family.key,
1763
+ type: `writable_held_selector_family`
1764
+ };
1765
+ const family = withdraw(store, familyToken);
1766
+ family.subject.next({
1767
+ type: `state_disposal`,
1768
+ subType: `selector`,
1769
+ token: selectorToken
1770
+ });
1771
+ }
1772
+ break;
1773
+ case `writable_pure_selector`:
1774
+ {
1775
+ target.writableSelectors.delete(key);
1776
+ familyToken = {
1777
+ key: selector.family.key,
1778
+ type: `writable_pure_selector_family`
1779
+ };
1780
+ const family = withdraw(store, familyToken);
1781
+ family.subject.next({
1782
+ type: `state_disposal`,
1783
+ subType: `selector`,
1784
+ token: selectorToken
1785
+ });
1786
+ }
1787
+ break;
1788
+ case `readonly_held_selector`:
1789
+ {
1790
+ target.readonlySelectors.delete(key);
1791
+ familyToken = {
1792
+ key: selector.family.key,
1793
+ type: `readonly_held_selector_family`
1794
+ };
1795
+ const family = withdraw(store, familyToken);
1796
+ family.subject.next({
1797
+ type: `state_disposal`,
1798
+ subType: `selector`,
1799
+ token: selectorToken
1800
+ });
1801
+ }
1802
+ break;
1803
+ case `readonly_pure_selector`:
1804
+ {
1805
+ target.readonlySelectors.delete(key);
1806
+ familyToken = {
1807
+ key: selector.family.key,
1808
+ type: `readonly_pure_selector_family`
1809
+ };
1810
+ const family = withdraw(store, familyToken);
1811
+ family.subject.next({
1812
+ type: `state_disposal`,
1813
+ subType: `selector`,
1814
+ token: selectorToken
1815
+ });
1816
+ }
1817
+ break;
1818
+ }
1819
+ target.valueMap.delete(key);
1820
+ target.selectorAtoms.delete(key);
1821
+ target.selectorGraph.delete(key);
1822
+ store.logger.info(`🔥`, selectorToken.type, key, `deleted`);
1823
+ if (isChildStore(target) && target.transactionMeta.phase === `building`) target.transactionMeta.update.updates.push({
1824
+ type: `state_disposal`,
1825
+ subType: `selector`,
1826
+ token: selectorToken
1827
+ });
1828
+ else store.on.selectorDisposal.next(selectorToken);
1829
+ }
1830
+ }
1989
1831
 
1990
1832
  //#endregion
1991
- //#region src/internal/transaction/create-transaction.ts
1992
- function createTransaction(store, options) {
1993
- const { key } = options;
1994
- const transactionAlreadyExists = store.transactions.has(key);
1995
- const newTransaction = {
1996
- key,
1997
- type: `transaction`,
1998
- run: (params, id) => {
1999
- const childStore = buildTransaction(store, key, params, id);
2000
- try {
2001
- const target$1 = newest(store);
2002
- const { toolkit } = childStore.transactionMeta;
2003
- const output = options.do(toolkit, ...params);
2004
- applyTransaction(output, target$1);
2005
- return output;
2006
- } catch (thrown) {
2007
- abortTransaction(target);
2008
- store.logger.warn(`💥`, `transaction`, key, `caught:`, thrown);
2009
- throw thrown;
2010
- }
2011
- },
2012
- install: (s) => createTransaction(s, options),
2013
- subject: new Subject()
1833
+ //#region src/internal/families/create-readonly-pure-selector-family.ts
1834
+ function createReadonlyPureSelectorFamily(store, options, internalRoles) {
1835
+ const familyKey = options.key;
1836
+ const type = `readonly_pure_selector_family`;
1837
+ const familyToken = {
1838
+ key: familyKey,
1839
+ type
2014
1840
  };
2015
- const target = newest(store);
2016
- target.transactions.set(key, newTransaction);
2017
- const token = deposit(newTransaction);
2018
- if (!transactionAlreadyExists) store.on.transactionCreation.next(token);
2019
- return token;
1841
+ const existing = store.families.get(familyKey);
1842
+ if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1843
+ const subject = new Subject();
1844
+ const familyFunction = (key) => {
1845
+ const subKey = stringifyJson(key);
1846
+ const family = {
1847
+ key: familyKey,
1848
+ subKey
1849
+ };
1850
+ const fullKey = `${familyKey}(${subKey})`;
1851
+ const target = newest(store);
1852
+ const token = createReadonlyPureSelector(target, {
1853
+ key: fullKey,
1854
+ get: options.get(key)
1855
+ }, family);
1856
+ subject.next({
1857
+ type: `state_creation`,
1858
+ token
1859
+ });
1860
+ return token;
1861
+ };
1862
+ const readonlySelectorFamily = Object.assign(familyFunction, familyToken, {
1863
+ internalRoles,
1864
+ subject,
1865
+ install: (s) => createReadonlyPureSelectorFamily(s, options),
1866
+ default: (key) => {
1867
+ const getFn = options.get(key);
1868
+ return getFn({
1869
+ get: ((...args) => getFromStore(store, ...args)),
1870
+ find: ((...args) => findInStore(store, ...args)),
1871
+ json: (token) => getJsonToken(store, token)
1872
+ });
1873
+ }
1874
+ });
1875
+ store.families.set(familyKey, readonlySelectorFamily);
1876
+ return familyToken;
2020
1877
  }
2021
1878
 
2022
1879
  //#endregion
2023
- //#region src/internal/transaction/index.ts
2024
- const TRANSACTION_PHASES = [
2025
- `idle`,
2026
- `building`,
2027
- `applying`
2028
- ];
2029
-
2030
- //#endregion
2031
- //#region src/internal/store/store.ts
2032
- var Store = class {
2033
- parent = null;
2034
- child = null;
2035
- valueMap = /* @__PURE__ */ new Map();
2036
- defaults = /* @__PURE__ */ new Map();
2037
- atoms = /* @__PURE__ */ new Map();
2038
- writableSelectors = /* @__PURE__ */ new Map();
2039
- readonlySelectors = /* @__PURE__ */ new Map();
2040
- atomsThatAreDefault = /* @__PURE__ */ new Set();
2041
- selectorAtoms = new Junction({
2042
- between: [`selectorKey`, `atomKey`],
2043
- cardinality: `n:n`
2044
- });
2045
- selectorGraph = new Junction({
2046
- between: [`upstreamSelectorKey`, `downstreamSelectorKey`],
2047
- cardinality: `n:n`
2048
- }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2049
- trackers = /* @__PURE__ */ new Map();
2050
- families = /* @__PURE__ */ new Map();
2051
- joins = /* @__PURE__ */ new Map();
2052
- transactions = /* @__PURE__ */ new Map();
2053
- transactionMeta = {
2054
- epoch: /* @__PURE__ */ new Map(),
2055
- actionContinuities: new Junction({
2056
- between: [`continuity`, `action`],
2057
- cardinality: `1:n`
2058
- })
1880
+ //#region src/internal/families/create-readonly-held-selector-family.ts
1881
+ function createReadonlyHeldSelectorFamily(store, options, internalRoles) {
1882
+ const familyKey = options.key;
1883
+ const type = `readonly_held_selector_family`;
1884
+ const familyToken = {
1885
+ key: familyKey,
1886
+ type
2059
1887
  };
2060
- timelines = /* @__PURE__ */ new Map();
2061
- timelineTopics = new Junction({
2062
- between: [`timelineKey`, `topicKey`],
2063
- cardinality: `1:n`
2064
- });
2065
- disposalTraces = new CircularBuffer(100);
2066
- molecules = /* @__PURE__ */ new Map();
2067
- moleculeJoins = new Junction({
2068
- between: [`moleculeKey`, `joinKey`],
2069
- cardinality: `n:n`
2070
- }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2071
- moleculeGraph = new Junction({
2072
- between: [`upstreamMoleculeKey`, `downstreamMoleculeKey`],
2073
- cardinality: `n:n`
2074
- }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2075
- moleculeData = new Junction({
2076
- between: [`moleculeKey`, `stateFamilyKey`],
2077
- cardinality: `n:n`
2078
- }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2079
- miscResources = /* @__PURE__ */ new Map();
2080
- on = {
2081
- atomCreation: new Subject(),
2082
- atomDisposal: new Subject(),
2083
- selectorCreation: new Subject(),
2084
- selectorDisposal: new Subject(),
2085
- timelineCreation: new Subject(),
2086
- transactionCreation: new Subject(),
2087
- transactionApplying: new StatefulSubject(null),
2088
- operationClose: new Subject(),
2089
- moleculeCreation: new Subject(),
2090
- moleculeDisposal: new Subject()
1888
+ const existing = store.families.get(familyKey);
1889
+ if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1890
+ const subject = new Subject();
1891
+ const familyFunction = (key) => {
1892
+ const subKey = stringifyJson(key);
1893
+ const family = {
1894
+ key: familyKey,
1895
+ subKey
1896
+ };
1897
+ const fullKey = `${familyKey}(${subKey})`;
1898
+ const target = newest(store);
1899
+ const token = createReadonlyHeldSelector(target, {
1900
+ key: fullKey,
1901
+ const: options.const(key),
1902
+ get: options.get(key)
1903
+ }, family);
1904
+ subject.next({
1905
+ type: `state_creation`,
1906
+ token
1907
+ });
1908
+ return token;
2091
1909
  };
2092
- operation = { open: false };
2093
- config = {
2094
- name: `IMPLICIT_STORE`,
2095
- lifespan: `ephemeral`
1910
+ const readonlySelectorFamily = Object.assign(familyFunction, familyToken, {
1911
+ internalRoles,
1912
+ subject,
1913
+ install: (s) => createReadonlyHeldSelectorFamily(s, options),
1914
+ default: options.const
1915
+ });
1916
+ store.families.set(familyKey, readonlySelectorFamily);
1917
+ return familyToken;
1918
+ }
1919
+
1920
+ //#endregion
1921
+ //#region src/internal/families/create-writable-held-selector-family.ts
1922
+ function createWritableHeldSelectorFamily(store, options, internalRoles) {
1923
+ const familyKey = options.key;
1924
+ const type = `writable_held_selector_family`;
1925
+ const familyToken = {
1926
+ key: familyKey,
1927
+ type
2096
1928
  };
2097
- loggers = [new AtomIOLogger(`warn`, (_, __, key) => !isReservedIntrospectionKey(key))];
2098
- logger = {
2099
- error: (...messages) => {
2100
- for (const logger of this.loggers) logger.error(...messages);
2101
- },
2102
- info: (...messages) => {
2103
- for (const logger of this.loggers) logger.info(...messages);
2104
- },
2105
- warn: (...messages) => {
2106
- for (const logger of this.loggers) logger.warn(...messages);
2107
- }
1929
+ const existing = store.families.get(familyKey);
1930
+ if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1931
+ const subject = new Subject();
1932
+ const familyFunction = (key) => {
1933
+ const subKey = stringifyJson(key);
1934
+ const family = {
1935
+ key: familyKey,
1936
+ subKey
1937
+ };
1938
+ const fullKey = `${familyKey}(${subKey})`;
1939
+ const target = newest(store);
1940
+ const token = createWritableHeldSelector(target, {
1941
+ key: fullKey,
1942
+ const: options.const(key),
1943
+ get: options.get(key),
1944
+ set: options.set(key)
1945
+ }, family);
1946
+ subject.next({
1947
+ type: `state_creation`,
1948
+ token
1949
+ });
1950
+ return token;
2108
1951
  };
2109
- constructor(config, store = null) {
2110
- this.config = {
2111
- ...store?.config,
2112
- ...config
1952
+ const selectorFamily$1 = Object.assign(familyFunction, familyToken, {
1953
+ internalRoles,
1954
+ subject,
1955
+ install: (s) => createWritableHeldSelectorFamily(s, options),
1956
+ default: options.const
1957
+ });
1958
+ store.families.set(familyKey, selectorFamily$1);
1959
+ return familyToken;
1960
+ }
1961
+
1962
+ //#endregion
1963
+ //#region src/internal/families/create-writable-pure-selector-family.ts
1964
+ function createWritablePureSelectorFamily(store, options, internalRoles) {
1965
+ const familyKey = options.key;
1966
+ const type = `writable_pure_selector_family`;
1967
+ const familyToken = {
1968
+ key: familyKey,
1969
+ type
1970
+ };
1971
+ const existing = store.families.get(familyKey);
1972
+ if (existing) store.logger.error(`❗`, type, familyKey, `Overwriting an existing ${prettyPrintTokenType(existing)} "${existing.key}" in store "${store.config.name}". You can safely ignore this warning if it is due to hot module replacement.`);
1973
+ const subject = new Subject();
1974
+ const familyFunction = (key) => {
1975
+ const subKey = stringifyJson(key);
1976
+ const family = {
1977
+ key: familyKey,
1978
+ subKey
2113
1979
  };
2114
- if (store !== null) {
2115
- this.valueMap = new Map(store?.valueMap);
2116
- this.operation = { ...store?.operation };
2117
- if (isRootStore(store)) this.transactionMeta = {
2118
- epoch: new Map(store?.transactionMeta.epoch),
2119
- actionContinuities: new Junction(store?.transactionMeta.actionContinuities.toJSON())
2120
- };
2121
- for (const [, family] of store.families) {
2122
- if (family.internalRoles?.includes(`mutable`) || family.internalRoles?.includes(`join`)) continue;
2123
- family.install(this);
2124
- }
2125
- const mutableHelpers = /* @__PURE__ */ new Set();
2126
- for (const [, atom$1] of store.atoms) {
2127
- if (mutableHelpers.has(atom$1.key)) continue;
2128
- atom$1.install(this);
2129
- if (atom$1.type === `mutable_atom`) {
2130
- const originalJsonToken = getJsonToken(store, atom$1);
2131
- const originalUpdateToken = getUpdateToken(atom$1);
2132
- mutableHelpers.add(originalJsonToken.key);
2133
- mutableHelpers.add(originalUpdateToken.key);
2134
- }
2135
- }
2136
- for (const [, selector] of store.readonlySelectors) selector.install(this);
2137
- for (const [, selector] of store.writableSelectors) {
2138
- if (mutableHelpers.has(selector.key)) continue;
2139
- selector.install(this);
2140
- }
2141
- for (const [, tx] of store.transactions) tx.install(this);
2142
- for (const [, timeline] of store.timelines) timeline.install(this);
1980
+ const fullKey = `${familyKey}(${subKey})`;
1981
+ const target = newest(store);
1982
+ const token = createWritablePureSelector(target, {
1983
+ key: fullKey,
1984
+ get: options.get(key),
1985
+ set: options.set(key)
1986
+ }, family);
1987
+ subject.next({
1988
+ type: `state_creation`,
1989
+ token
1990
+ });
1991
+ return token;
1992
+ };
1993
+ const selectorFamily$1 = Object.assign(familyFunction, familyToken, {
1994
+ internalRoles,
1995
+ subject,
1996
+ install: (s) => createWritablePureSelectorFamily(s, options),
1997
+ default: (key) => {
1998
+ const getFn = options.get(key);
1999
+ return getFn({
2000
+ get: ((...args) => getFromStore(store, ...args)),
2001
+ find: ((...args) => findInStore(store, ...args)),
2002
+ json: (token) => getJsonToken(store, token)
2003
+ });
2143
2004
  }
2144
- }
2145
- };
2146
- const IMPLICIT = { get STORE() {
2147
- globalThis.ATOM_IO_IMPLICIT_STORE ??= new Store({
2148
- name: `IMPLICIT_STORE`,
2149
- lifespan: `ephemeral`
2150
2005
  });
2151
- return globalThis.ATOM_IO_IMPLICIT_STORE;
2152
- } };
2153
- const clearStore = (store) => {
2154
- const { config } = store;
2155
- for (const disposable of store.miscResources.values()) disposable[Symbol.dispose]();
2156
- Object.assign(store, new Store(config));
2157
- store.config = config;
2158
- };
2006
+ store.families.set(familyKey, selectorFamily$1);
2007
+ return familyToken;
2008
+ }
2159
2009
 
2160
2010
  //#endregion
2161
- //#region src/internal/store/withdraw.ts
2162
- function withdraw(store, token) {
2163
- let withdrawn;
2164
- let target = store;
2165
- while (target !== null) {
2166
- switch (token.type) {
2011
+ //#region src/internal/families/create-selector-family.ts
2012
+ function createSelectorFamily(store, options) {
2013
+ const isWritable = `set` in options;
2014
+ const isHeld = `const` in options;
2015
+ if (isHeld && isWritable) return createWritableHeldSelectorFamily(store, options, void 0);
2016
+ if (isHeld) return createReadonlyHeldSelectorFamily(store, options, void 0);
2017
+ if (isWritable) return createWritablePureSelectorFamily(store, options);
2018
+ return createReadonlyPureSelectorFamily(store, options);
2019
+ }
2020
+
2021
+ //#endregion
2022
+ //#region src/internal/families/init-family-member.ts
2023
+ function initFamilyMemberInStore(store, token, key) {
2024
+ const family = store.families.get(token.key);
2025
+ if (family === void 0) throw new NotFoundError(token, store);
2026
+ const state = family(key);
2027
+ const target = newest(store);
2028
+ if (state.family) {
2029
+ if (isRootStore(target)) switch (state.type) {
2167
2030
  case `atom`:
2168
2031
  case `mutable_atom`:
2169
- withdrawn = target.atoms.get(token.key);
2032
+ store.on.atomCreation.next(state);
2170
2033
  break;
2171
2034
  case `writable_pure_selector`:
2172
- case `writable_held_selector`:
2173
- withdrawn = target.writableSelectors.get(token.key);
2174
- break;
2175
2035
  case `readonly_pure_selector`:
2036
+ case `writable_held_selector`:
2176
2037
  case `readonly_held_selector`:
2177
- withdrawn = target.readonlySelectors.get(token.key);
2178
- break;
2179
- case `atom_family`:
2180
- case `mutable_atom_family`:
2181
- case `writable_pure_selector_family`:
2182
- case `readonly_pure_selector_family`:
2183
- case `writable_held_selector_family`:
2184
- case `readonly_held_selector_family`:
2185
- withdrawn = target.families.get(token.key);
2186
- break;
2187
- case `timeline`:
2188
- withdrawn = target.timelines.get(token.key);
2189
- break;
2190
- case `transaction`:
2191
- withdrawn = target.transactions.get(token.key);
2038
+ store.on.selectorCreation.next(state);
2192
2039
  break;
2193
2040
  }
2194
- if (withdrawn) return withdrawn;
2195
- target = target.child;
2041
+ else if (isChildStore(target) && target.on.transactionApplying.state === null) target.transactionMeta.update.updates.push({
2042
+ type: `state_creation`,
2043
+ token: state
2044
+ });
2196
2045
  }
2197
- throw new NotFoundError(token, store);
2046
+ return state;
2198
2047
  }
2199
2048
 
2200
2049
  //#endregion
2201
- //#region src/internal/subscribe/recall-state.ts
2202
- const recallState = (store, state) => {
2050
+ //#region src/internal/families/seek-in-store.ts
2051
+ function seekInStore(store, token, key) {
2052
+ const subKey = stringifyJson(key);
2053
+ const fullKey = `${token.key}(${subKey})`;
2203
2054
  const target = newest(store);
2204
- if (target.operation.open) return target.operation.prev.get(state.key);
2205
- return target.valueMap.get(state.key);
2206
- };
2055
+ let state;
2056
+ switch (token.type) {
2057
+ case `atom_family`:
2058
+ case `mutable_atom_family`:
2059
+ state = target.atoms.get(fullKey);
2060
+ break;
2061
+ case `writable_held_selector_family`:
2062
+ case `writable_pure_selector_family`:
2063
+ state = target.writableSelectors.get(fullKey);
2064
+ break;
2065
+ case `readonly_held_selector_family`:
2066
+ case `readonly_pure_selector_family`:
2067
+ state = target.readonlySelectors.get(fullKey);
2068
+ break;
2069
+ }
2070
+ if (state) return deposit(state);
2071
+ return state;
2072
+ }
2207
2073
 
2208
2074
  //#endregion
2209
- //#region src/internal/subscribe/subscribe-in-store.ts
2210
- function subscribeInStore(store, token, handleUpdate, key = arbitrary$1()) {
2075
+ //#region src/internal/families/find-in-store.ts
2076
+ function findInStore(store, token, key) {
2077
+ let state = seekInStore(store, token, key);
2078
+ if (state) return state;
2079
+ const stringKey = stringifyJson(key);
2080
+ const molecule = store.molecules.get(stringKey);
2081
+ if (!molecule && store.config.lifespan === `immortal`) {
2082
+ const fakeToken = counterfeit(token, key);
2083
+ store.logger.error(`❌`, fakeToken.type, fakeToken.key, `was not found in store "${store.config.name}"; returned a counterfeit token.`);
2084
+ return fakeToken;
2085
+ }
2086
+ state = initFamilyMemberInStore(store, token, key);
2087
+ if (molecule) {
2088
+ const target = newest(store);
2089
+ target.moleculeData.set(stringKey, token.key);
2090
+ }
2091
+ return state;
2092
+ }
2093
+
2094
+ //#endregion
2095
+ //#region src/internal/families/dispose-from-store.ts
2096
+ function disposeFromStore(store, ...params) {
2097
+ let token;
2098
+ if (params.length === 1) token = params[0];
2099
+ else {
2100
+ const family = params[0];
2101
+ const key = params[1];
2102
+ const maybeToken = findInStore(store, family, key);
2103
+ token = maybeToken;
2104
+ }
2105
+ try {
2106
+ withdraw(store, token);
2107
+ } catch (_) {
2108
+ store.logger.error(`❌`, token.type, token.key, `could not be disposed because it was not found in the store "${store.config.name}".`);
2109
+ return;
2110
+ }
2211
2111
  switch (token.type) {
2212
2112
  case `atom`:
2213
2113
  case `mutable_atom`:
2114
+ disposeAtom(store, token);
2115
+ break;
2116
+ case `writable_pure_selector`:
2214
2117
  case `readonly_pure_selector`:
2118
+ case `writable_held_selector`:
2215
2119
  case `readonly_held_selector`:
2216
- case `writable_pure_selector`:
2217
- case `writable_held_selector`: return subscribeToState$1(store, token, key, handleUpdate);
2218
- case `transaction`: return subscribeToTransaction$1(store, token, key, handleUpdate);
2219
- case `timeline`: return subscribeToTimeline$1(store, token, key, handleUpdate);
2120
+ disposeSelector(store, token);
2121
+ break;
2122
+ }
2123
+ }
2124
+
2125
+ //#endregion
2126
+ //#region src/internal/get-state/get-from-store.ts
2127
+ function getFromStore(store, ...params) {
2128
+ let token;
2129
+ let family;
2130
+ let key;
2131
+ if (params.length === 1) token = params[0];
2132
+ else {
2133
+ family = params[0];
2134
+ key = params[1];
2135
+ token = findInStore(store, family, key);
2136
+ }
2137
+ if (`counterfeit` in token && `family` in token) {
2138
+ family = store.families.get(token.family.key);
2139
+ const subKey = token.family.subKey;
2140
+ const disposal = store.disposalTraces.buffer.find((item) => item?.key === subKey);
2141
+ store.logger.error(`❌`, token.type, token.key, `could not be retrieved because it was not found in the store "${store.config.name}".`, disposal ? `This state was previously disposed:\n${disposal.trace}` : `No previous disposal trace was found.`);
2142
+ switch (family.type) {
2143
+ case `atom_family`:
2144
+ case `mutable_atom_family`: return store.defaults.get(family.key);
2145
+ case `readonly_pure_selector_family`:
2146
+ case `writable_pure_selector_family`:
2147
+ case `readonly_held_selector_family`:
2148
+ case `writable_held_selector_family`: {
2149
+ if (store.defaults.has(family.key)) return store.defaults.get(token.family.key);
2150
+ const defaultValue = withdraw(store, family).default(subKey);
2151
+ store.defaults.set(family.key, defaultValue);
2152
+ return defaultValue;
2153
+ }
2154
+ }
2220
2155
  }
2156
+ return readOrComputeValue(store, withdraw(store, token));
2221
2157
  }
2222
2158
 
2223
- //#endregion
2224
- //#region src/internal/subscribe/subscribe-to-root-atoms.ts
2225
- const subscribeToRootAtoms = (store, selector) => {
2226
- const target = newest(store);
2227
- const dependencySubscriptions = traceAllSelectorAtoms(selector, store).map((atom$1) => {
2228
- return atom$1.subject.subscribe(`${selector.type}:${selector.key}`, (atomChange) => {
2229
- store.logger.info(`📢`, selector.type, selector.key, `root`, atom$1.key, `went`, atomChange.oldValue, `->`, atomChange.newValue);
2230
- const oldValue = recallState(target, selector);
2231
- const newValue = readOrComputeValue(target, selector);
2232
- store.logger.info(`✨`, selector.type, selector.key, `went`, oldValue, `->`, newValue);
2233
- selector.subject.next({
2234
- newValue,
2235
- oldValue
2236
- });
2237
- });
2238
- });
2239
- return dependencySubscriptions;
2240
- };
2241
-
2242
2159
  //#endregion
2243
2160
  //#region src/internal/subscribe/subscribe-to-state.ts
2244
2161
  function subscribeToState(store, token, key, handleUpdate) {
@@ -2253,15 +2170,22 @@ function subscribeToState(store, token, key, handleUpdate) {
2253
2170
  const state = withdraw(store, token);
2254
2171
  store.logger.info(`👀`, state.type, state.key, `Adding subscription "${key}"`);
2255
2172
  const isSelector = state.type === `writable_pure_selector` || state.type === `readonly_pure_selector`;
2256
- let dependencyUnsubFunctions = null;
2173
+ const rootSubs = /* @__PURE__ */ new Map();
2257
2174
  let updateHandler = safelyHandleUpdate;
2258
2175
  if (isSelector) {
2259
- dependencyUnsubFunctions = subscribeToRootAtoms(store, state);
2260
- updateHandler = (update) => {
2261
- if (dependencyUnsubFunctions) {
2262
- dependencyUnsubFunctions.length = 0;
2263
- dependencyUnsubFunctions.push(...subscribeToRootAtoms(store, state));
2176
+ readOrComputeValue(store, state);
2177
+ for (const [atomKey, atom$1] of traceRootSelectorAtoms(store, state.key)) rootSubs.set(atomKey, subscribeToRootDependency(store, state, atom$1));
2178
+ updateHandler = function updateRootsBeforeHandlingUpdate(update) {
2179
+ const dependencies = traceRootSelectorAtoms(store, state.key);
2180
+ for (const [previousRootKey, unsub] of rootSubs) {
2181
+ const currentRoot = dependencies.get(previousRootKey);
2182
+ if (currentRoot) dependencies.delete(previousRootKey);
2183
+ else {
2184
+ unsub();
2185
+ rootSubs.delete(previousRootKey);
2186
+ }
2264
2187
  }
2188
+ for (const [atomKey, atom$1] of dependencies) rootSubs.set(atomKey, subscribeToRootDependency(store, state, atom$1));
2265
2189
  safelyHandleUpdate(update);
2266
2190
  };
2267
2191
  }
@@ -2269,7 +2193,7 @@ function subscribeToState(store, token, key, handleUpdate) {
2269
2193
  const unsubscribe = () => {
2270
2194
  store.logger.info(`🙈`, state.type, state.key, `Removing subscription "${key}"`);
2271
2195
  mainUnsubFunction();
2272
- if (dependencyUnsubFunctions) for (const unsubFromDependency of dependencyUnsubFunctions) unsubFromDependency();
2196
+ for (const unsubFromDependency of rootSubs.values()) unsubFromDependency();
2273
2197
  };
2274
2198
  return unsubscribe;
2275
2199
  }
@@ -2395,7 +2319,7 @@ var Tracker = class {
2395
2319
  function createMutableAtom(store, options, family) {
2396
2320
  store.logger.info(`🔨`, `atom`, options.key, `creating in store "${store.config.name}"`);
2397
2321
  const target = newest(store);
2398
- const { key, default: def } = options;
2322
+ const { key } = options;
2399
2323
  const existing = target.atoms.get(key);
2400
2324
  const type = `mutable_atom`;
2401
2325
  if (existing && existing.type === type) {
@@ -2413,9 +2337,7 @@ function createMutableAtom(store, options, family) {
2413
2337
  subject
2414
2338
  };
2415
2339
  if (family) newAtom.family = family;
2416
- const initialValue = def();
2417
2340
  target.atoms.set(newAtom.key, newAtom);
2418
- cacheValue(target, key, initialValue, subject);
2419
2341
  const token = deposit(newAtom);
2420
2342
  if (options.effects) {
2421
2343
  let effectIndex = 0;
@@ -2586,90 +2508,179 @@ function isTransceiver(value) {
2586
2508
  }
2587
2509
 
2588
2510
  //#endregion
2589
- //#region src/internal/set-state/copy-mutable-if-needed.ts
2590
- function copyMutableIfNeeded(target, atom$1, origin) {
2591
- const originValue = origin.valueMap.get(atom$1.key);
2592
- const targetValue = target.valueMap.get(atom$1.key);
2593
- if (originValue !== targetValue) return targetValue;
2594
- if (originValue === void 0) return atom$1.default();
2595
- origin.logger.info(`📃`, `atom`, atom$1.key, `copying`);
2596
- const jsonValue = atom$1.toJson(originValue);
2597
- const copiedValue = atom$1.fromJson(jsonValue);
2598
- target.valueMap.set(atom$1.key, copiedValue);
2599
- new Tracker(atom$1, origin);
2600
- return copiedValue;
2601
- }
2602
-
2603
- //#endregion
2604
- //#region src/internal/caching.ts
2605
- function cacheValue(target, key, value, subject) {
2606
- const currentValue = target.valueMap.get(key);
2607
- if (currentValue instanceof Future) {
2608
- const future = currentValue;
2609
- if (value instanceof Promise) return future;
2610
- target.valueMap.set(key, value);
2611
- return value;
2612
- }
2613
- if (value instanceof Promise) {
2614
- const future = new Future(value);
2615
- target.valueMap.set(key, future);
2616
- future.then((resolved) => {
2617
- const current = target.valueMap.get(key);
2618
- if (current === future) {
2619
- cacheValue(target, key, resolved, subject);
2620
- const atom$1 = target.atoms.get(key);
2621
- if (atom$1) {
2622
- openOperation(target, atom$1);
2623
- evictDownStream(target, atom$1);
2624
- closeOperation(target);
2625
- } else {
2626
- const selector = target.writableSelectors.get(key) ?? target.readonlySelectors.get(key);
2627
- if (selector) {
2628
- openOperation(target, selector);
2629
- evictDownStreamFromSelector(target, selector);
2630
- closeOperation(target);
2631
- }
2511
+ //#region src/internal/store/store.ts
2512
+ var Store = class {
2513
+ parent = null;
2514
+ child = null;
2515
+ valueMap = /* @__PURE__ */ new Map();
2516
+ defaults = /* @__PURE__ */ new Map();
2517
+ atoms = /* @__PURE__ */ new Map();
2518
+ writableSelectors = /* @__PURE__ */ new Map();
2519
+ readonlySelectors = /* @__PURE__ */ new Map();
2520
+ atomsThatAreDefault = /* @__PURE__ */ new Set();
2521
+ selectorAtoms = new Junction({
2522
+ between: [`selectorKey`, `atomKey`],
2523
+ cardinality: `n:n`
2524
+ });
2525
+ selectorGraph = new Junction({
2526
+ between: [`upstreamSelectorKey`, `downstreamSelectorKey`],
2527
+ cardinality: `n:n`
2528
+ }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2529
+ trackers = /* @__PURE__ */ new Map();
2530
+ families = /* @__PURE__ */ new Map();
2531
+ joins = /* @__PURE__ */ new Map();
2532
+ transactions = /* @__PURE__ */ new Map();
2533
+ transactionMeta = {
2534
+ epoch: /* @__PURE__ */ new Map(),
2535
+ actionContinuities: new Junction({
2536
+ between: [`continuity`, `action`],
2537
+ cardinality: `1:n`
2538
+ })
2539
+ };
2540
+ timelines = /* @__PURE__ */ new Map();
2541
+ timelineTopics = new Junction({
2542
+ between: [`timelineKey`, `topicKey`],
2543
+ cardinality: `1:n`
2544
+ });
2545
+ disposalTraces = new CircularBuffer(100);
2546
+ molecules = /* @__PURE__ */ new Map();
2547
+ moleculeJoins = new Junction({
2548
+ between: [`moleculeKey`, `joinKey`],
2549
+ cardinality: `n:n`
2550
+ }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2551
+ moleculeGraph = new Junction({
2552
+ between: [`upstreamMoleculeKey`, `downstreamMoleculeKey`],
2553
+ cardinality: `n:n`
2554
+ }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2555
+ moleculeData = new Junction({
2556
+ between: [`moleculeKey`, `stateFamilyKey`],
2557
+ cardinality: `n:n`
2558
+ }, { makeContentKey: (...keys) => keys.sort().join(`:`) });
2559
+ miscResources = /* @__PURE__ */ new Map();
2560
+ on = {
2561
+ atomCreation: new Subject(),
2562
+ atomDisposal: new Subject(),
2563
+ selectorCreation: new Subject(),
2564
+ selectorDisposal: new Subject(),
2565
+ timelineCreation: new Subject(),
2566
+ transactionCreation: new Subject(),
2567
+ transactionApplying: new StatefulSubject(null),
2568
+ operationClose: new Subject(),
2569
+ moleculeCreation: new Subject(),
2570
+ moleculeDisposal: new Subject()
2571
+ };
2572
+ operation = { open: false };
2573
+ config = {
2574
+ name: `IMPLICIT_STORE`,
2575
+ lifespan: `ephemeral`
2576
+ };
2577
+ loggers = [new AtomIOLogger(`warn`, (_, __, key) => !isReservedIntrospectionKey(key))];
2578
+ logger = {
2579
+ error: (...messages) => {
2580
+ for (const logger of this.loggers) logger.error(...messages);
2581
+ },
2582
+ info: (...messages) => {
2583
+ for (const logger of this.loggers) logger.info(...messages);
2584
+ },
2585
+ warn: (...messages) => {
2586
+ for (const logger of this.loggers) logger.warn(...messages);
2587
+ }
2588
+ };
2589
+ constructor(config, store = null) {
2590
+ this.config = {
2591
+ ...store?.config,
2592
+ ...config
2593
+ };
2594
+ if (store !== null) {
2595
+ this.operation = { ...store?.operation };
2596
+ if (isRootStore(store)) this.transactionMeta = {
2597
+ epoch: new Map(store?.transactionMeta.epoch),
2598
+ actionContinuities: new Junction(store?.transactionMeta.actionContinuities.toJSON())
2599
+ };
2600
+ for (const [, family] of store.families) {
2601
+ if (family.internalRoles?.includes(`mutable`) || family.internalRoles?.includes(`join`)) continue;
2602
+ family.install(this);
2603
+ }
2604
+ const mutableHelpers = /* @__PURE__ */ new Set();
2605
+ for (const [, atom$1] of store.atoms) {
2606
+ if (mutableHelpers.has(atom$1.key)) continue;
2607
+ atom$1.install(this);
2608
+ if (atom$1.type === `mutable_atom`) {
2609
+ const originalJsonToken = getJsonToken(store, atom$1);
2610
+ const originalUpdateToken = getUpdateToken(atom$1);
2611
+ mutableHelpers.add(originalJsonToken.key);
2612
+ mutableHelpers.add(originalUpdateToken.key);
2632
2613
  }
2633
- subject.next({
2634
- newValue: resolved,
2635
- oldValue: future
2636
- });
2637
2614
  }
2638
- }).catch((thrown) => {
2639
- target.logger.error(`💥`, `state`, key, `rejected:`, thrown);
2640
- });
2641
- return future;
2642
- }
2643
- target.valueMap.set(key, value);
2644
- return value;
2645
- }
2646
- const readCachedValue = (token, target) => {
2647
- let value = target.valueMap.get(token.key);
2648
- if (token.type === `mutable_atom` && isChildStore(target)) {
2649
- const { parent } = target;
2650
- const copiedValue = copyMutableIfNeeded(target, token, parent);
2651
- value = copiedValue;
2615
+ for (const [, selector] of store.readonlySelectors) selector.install(this);
2616
+ for (const [, selector] of store.writableSelectors) {
2617
+ if (mutableHelpers.has(selector.key)) continue;
2618
+ selector.install(this);
2619
+ }
2620
+ for (const [, tx] of store.transactions) tx.install(this);
2621
+ for (const [, timeline] of store.timelines) timeline.install(this);
2622
+ }
2652
2623
  }
2653
- return value;
2654
2624
  };
2655
- const evictCachedValue = (key, target) => {
2656
- const currentValue = target.valueMap.get(key);
2657
- if (currentValue instanceof Future) {
2658
- const future = currentValue;
2659
- const selector = target.writableSelectors.get(key) ?? target.readonlySelectors.get(key);
2660
- if (selector) future.use(selector.get());
2661
- return;
2662
- }
2663
- if (target.operation.open) target.operation.prev.set(key, currentValue);
2664
- target.valueMap.delete(key);
2665
- target.logger.info(`🗑`, `state`, key, `evicted`);
2625
+ const IMPLICIT = { get STORE() {
2626
+ globalThis.ATOM_IO_IMPLICIT_STORE ??= new Store({
2627
+ name: `IMPLICIT_STORE`,
2628
+ lifespan: `ephemeral`
2629
+ });
2630
+ return globalThis.ATOM_IO_IMPLICIT_STORE;
2631
+ } };
2632
+ const clearStore = (store) => {
2633
+ const { config } = store;
2634
+ for (const disposable of store.miscResources.values()) disposable[Symbol.dispose]();
2635
+ Object.assign(store, new Store(config));
2636
+ store.config = config;
2666
2637
  };
2667
2638
 
2639
+ //#endregion
2640
+ //#region src/internal/store/withdraw.ts
2641
+ function withdraw(store, token) {
2642
+ let withdrawn;
2643
+ let target = store;
2644
+ while (target !== null) {
2645
+ switch (token.type) {
2646
+ case `atom`:
2647
+ case `mutable_atom`:
2648
+ withdrawn = target.atoms.get(token.key);
2649
+ break;
2650
+ case `writable_pure_selector`:
2651
+ case `writable_held_selector`:
2652
+ withdrawn = target.writableSelectors.get(token.key);
2653
+ break;
2654
+ case `readonly_pure_selector`:
2655
+ case `readonly_held_selector`:
2656
+ withdrawn = target.readonlySelectors.get(token.key);
2657
+ break;
2658
+ case `atom_family`:
2659
+ case `mutable_atom_family`:
2660
+ case `writable_pure_selector_family`:
2661
+ case `readonly_pure_selector_family`:
2662
+ case `writable_held_selector_family`:
2663
+ case `readonly_held_selector_family`:
2664
+ withdrawn = target.families.get(token.key);
2665
+ break;
2666
+ case `timeline`:
2667
+ withdrawn = target.timelines.get(token.key);
2668
+ break;
2669
+ case `transaction`:
2670
+ withdrawn = target.transactions.get(token.key);
2671
+ break;
2672
+ }
2673
+ if (withdrawn) return withdrawn;
2674
+ target = target.child;
2675
+ }
2676
+ throw new NotFoundError(token, store);
2677
+ }
2678
+
2668
2679
  //#endregion
2669
2680
  //#region src/internal/atom/create-regular-atom.ts
2670
2681
  function createRegularAtom(store, options, family) {
2671
2682
  const type = `atom`;
2672
- const { key, default: def } = options;
2683
+ const { key } = options;
2673
2684
  store.logger.info(`🔨`, `atom`, key, `creating in store "${store.config.name}"`);
2674
2685
  const target = newest(store);
2675
2686
  const existing = target.atoms.get(key);
@@ -2688,10 +2699,7 @@ function createRegularAtom(store, options, family) {
2688
2699
  subject
2689
2700
  };
2690
2701
  if (family) newAtom.family = family;
2691
- let initialValue = def;
2692
- if (def instanceof Function) initialValue = def();
2693
2702
  target.atoms.set(key, newAtom);
2694
- cacheValue(target, key, initialValue, subject);
2695
2703
  const token = deposit(newAtom);
2696
2704
  if (options.effects) {
2697
2705
  let effectIndex = 0;
@@ -3540,5 +3548,5 @@ const timeTravel = (store, action, token) => {
3540
3548
  };
3541
3549
 
3542
3550
  //#endregion
3543
- export { CircularBuffer, FAMILY_MEMBER_TOKEN_TYPES, FamilyTracker, Future, IMPLICIT, Join, Junction, LazyMap, NotFoundError, StatefulSubject, Store, Subject, TRANSACTION_PHASES, Tracker, abortTransaction, actUponStore, allocateIntoStore, applyTransaction, arbitrary, assignTransactionToContinuity, become, buildTransaction, cacheValue, capitalize, claimWithinStore, clearStore, closeOperation, counterfeit, createAtomFamily, createMutableAtom, createMutableAtomFamily, createReadonlyHeldSelector, createReadonlyPureSelector, createReadonlyPureSelectorFamily, createRegularAtom, createRegularAtomFamily, createSelectorFamily, createStandaloneAtom, createStandaloneSelector, createTimeline, createTransaction, createWritableHeldSelector, createWritablePureSelector, createWritablePureSelectorFamily, deallocateFromStore, deposit, disposeAtom, disposeFromStore, disposeSelector, editRelationsInStore, evictCachedValue, findInStore, findRelationsInStore, fuseWithinStore, getContinuityKey, getEnvironmentData, getEpochNumberOfAction, getEpochNumberOfContinuity, getFromStore, getInternalRelationsFromStore, getJoin, getJsonFamily, getJsonToken, getSelectorDependencyKeys, getTrace, getUpdateFamily, getUpdateToken, ingestAtomUpdate, ingestCreationEvent, ingestDisposalEvent, ingestMoleculeCreationEvent, ingestMoleculeDisposalEvent, ingestMoleculeTransferEvent, ingestSelectorUpdate, ingestTransactionUpdate, initFamilyMemberInStore, installIntoStore, isAtomKey, isChildStore, isDone, isReadonlySelectorKey, isReservedIntrospectionKey, isRootStore, isSelectorKey, isStateKey, isTransceiver, makeRootMoleculeInStore, markDone, newest, openOperation, prettyPrintTokenType, readCachedValue, readOrComputeValue, recallState, registerSelector, resetAtomOrSelector, resetInStore, seekInStore, setAtomOrSelector, setEpochNumberOfAction, setEpochNumberOfContinuity, setIntoStore, subscribeInStore, subscribeToRootAtoms, subscribeToState, subscribeToTimeline, subscribeToTransaction, timeTravel, traceAllSelectorAtoms, traceSelectorAtoms, updateSelectorAtoms, withdraw };
3551
+ export { CircularBuffer, FAMILY_MEMBER_TOKEN_TYPES, FamilyTracker, Future, IMPLICIT, Join, Junction, LazyMap, NotFoundError, StatefulSubject, Store, Subject, TRANSACTION_PHASES, Tracker, abortTransaction, actUponStore, allocateIntoStore, applyTransaction, arbitrary, assignTransactionToContinuity, become, buildTransaction, cacheValue, capitalize, claimWithinStore, clearStore, closeOperation, counterfeit, createAtomFamily, createMutableAtom, createMutableAtomFamily, createReadonlyHeldSelector, createReadonlyPureSelector, createReadonlyPureSelectorFamily, createRegularAtom, createRegularAtomFamily, createSelectorFamily, createStandaloneAtom, createStandaloneSelector, createTimeline, createTransaction, createWritableHeldSelector, createWritablePureSelector, createWritablePureSelectorFamily, deallocateFromStore, deposit, disposeAtom, disposeFromStore, disposeSelector, editRelationsInStore, evictCachedValue, findInStore, findRelationsInStore, fuseWithinStore, getContinuityKey, getEnvironmentData, getEpochNumberOfAction, getEpochNumberOfContinuity, getFromStore, getInternalRelationsFromStore, getJoin, getJsonFamily, getJsonToken, getSelectorDependencyKeys, getTrace, getUpdateFamily, getUpdateToken, ingestAtomUpdate, ingestCreationEvent, ingestDisposalEvent, ingestMoleculeCreationEvent, ingestMoleculeDisposalEvent, ingestMoleculeTransferEvent, ingestSelectorUpdate, ingestTransactionUpdate, initFamilyMemberInStore, installIntoStore, isAtomKey, isChildStore, isDone, isReadonlySelectorKey, isReservedIntrospectionKey, isRootStore, isSelectorKey, isStateKey, isTransceiver, makeRootMoleculeInStore, markDone, newest, openOperation, prettyPrintTokenType, readCachedValue, readOrComputeValue, recallState, registerSelector, resetAtomOrSelector, resetInStore, seekInStore, setAtomOrSelector, setEpochNumberOfAction, setEpochNumberOfContinuity, setIntoStore, subscribeInStore, subscribeToRootDependency, subscribeToState, subscribeToTimeline, subscribeToTransaction, timeTravel, traceRootSelectorAtoms, updateSelectorAtoms, withdraw };
3544
3552
  //# sourceMappingURL=index.js.map