atom.io 0.24.4 → 0.24.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +1 -1
- package/internal/dist/index.cjs +1449 -1403
- package/internal/dist/index.d.ts +10 -9
- package/internal/dist/index.js +1450 -1403
- package/internal/src/atom/dispose-atom.ts +5 -1
- package/internal/src/families/init-family-member.ts +11 -8
- package/internal/src/ingest-updates/ingest-creation-disposal.ts +22 -9
- package/internal/src/molecule/dispose-molecule.ts +27 -16
- package/internal/src/molecule/grow-molecule-in-store.ts +2 -6
- package/internal/src/molecule/make-molecule-in-store.ts +21 -15
- package/internal/src/mutable/tracker.ts +1 -1
- package/internal/src/selector/create-writable-selector.ts +9 -8
- package/internal/src/selector/dispose-selector.ts +4 -0
- package/internal/src/selector/register-selector.ts +3 -2
- package/internal/src/set-state/evict-downstream.ts +10 -8
- package/internal/src/store/store.ts +29 -25
- package/internal/src/timeline/create-timeline.ts +404 -104
- package/internal/src/timeline/index.ts +0 -1
- package/internal/src/transaction/apply-transaction.ts +0 -8
- package/internal/src/transaction/build-transaction.ts +2 -1
- package/package.json +1 -1
- package/realtime-server/dist/index.cjs +0 -61
- package/realtime-server/dist/index.js +3 -64
- package/realtime-server/src/realtime-server-stores/index.ts +0 -1
- package/src/transaction.ts +1 -1
- package/internal/src/timeline/add-atom-to-timeline.ts +0 -265
- package/realtime-server/src/realtime-server-stores/realtime-continuity-store.ts +0 -109
package/internal/dist/index.cjs
CHANGED
|
@@ -387,187 +387,69 @@ function isChildStore(store) {
|
|
|
387
387
|
return `phase` in store.transactionMeta;
|
|
388
388
|
}
|
|
389
389
|
|
|
390
|
-
// internal/src/
|
|
391
|
-
var
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
this.trackers = /* @__PURE__ */ new Map();
|
|
400
|
-
this.families = /* @__PURE__ */ new Map();
|
|
401
|
-
this.timelines = /* @__PURE__ */ new Map();
|
|
402
|
-
this.transactions = /* @__PURE__ */ new Map();
|
|
403
|
-
this.atomsThatAreDefault = /* @__PURE__ */ new Set();
|
|
404
|
-
this.timelineAtoms = new Junction({
|
|
405
|
-
between: [`timelineKey`, `atomKey`],
|
|
406
|
-
cardinality: `1:n`
|
|
407
|
-
});
|
|
408
|
-
this.selectorAtoms = new Junction({
|
|
409
|
-
between: [`selectorKey`, `atomKey`],
|
|
410
|
-
cardinality: `n:n`
|
|
411
|
-
});
|
|
412
|
-
this.selectorGraph = new Junction(
|
|
413
|
-
{
|
|
414
|
-
between: [`upstreamSelectorKey`, `downstreamSelectorKey`],
|
|
415
|
-
cardinality: `n:n`
|
|
416
|
-
},
|
|
417
|
-
{
|
|
418
|
-
makeContentKey: (...keys) => keys.sort().join(`:`)
|
|
419
|
-
}
|
|
390
|
+
// internal/src/transaction/abort-transaction.ts
|
|
391
|
+
var abortTransaction = (store) => {
|
|
392
|
+
const target = newest(store);
|
|
393
|
+
if (!isChildStore(target)) {
|
|
394
|
+
store.logger.warn(
|
|
395
|
+
`\u{1F41E}`,
|
|
396
|
+
`transaction`,
|
|
397
|
+
`???`,
|
|
398
|
+
`abortTransaction called outside of a transaction. This is probably a bug in AtomIO.`
|
|
420
399
|
);
|
|
421
|
-
|
|
422
|
-
this.moleculeFamilies = /* @__PURE__ */ new Map();
|
|
423
|
-
this.miscResources = /* @__PURE__ */ new Map();
|
|
424
|
-
this.on = {
|
|
425
|
-
atomCreation: new Subject(),
|
|
426
|
-
atomDisposal: new Subject(),
|
|
427
|
-
selectorCreation: new Subject(),
|
|
428
|
-
selectorDisposal: new Subject(),
|
|
429
|
-
timelineCreation: new Subject(),
|
|
430
|
-
transactionCreation: new Subject(),
|
|
431
|
-
transactionApplying: new StatefulSubject(
|
|
432
|
-
null
|
|
433
|
-
),
|
|
434
|
-
operationClose: new Subject(),
|
|
435
|
-
moleculeCreationStart: new Subject(),
|
|
436
|
-
moleculeCreationDone: new Subject(),
|
|
437
|
-
moleculeDisposal: new Subject()
|
|
438
|
-
};
|
|
439
|
-
this.operation = { open: false };
|
|
440
|
-
this.transactionMeta = {
|
|
441
|
-
epoch: /* @__PURE__ */ new Map(),
|
|
442
|
-
actionContinuities: new Junction({
|
|
443
|
-
between: [`continuity`, `action`],
|
|
444
|
-
cardinality: `1:n`
|
|
445
|
-
})
|
|
446
|
-
};
|
|
447
|
-
this.config = {
|
|
448
|
-
name: `IMPLICIT_STORE`,
|
|
449
|
-
lifespan: `ephemeral`
|
|
450
|
-
};
|
|
451
|
-
this.loggers = [
|
|
452
|
-
new atom_io.AtomIOLogger(`warn`, (_, __, key) => !key.includes(`\u{1F441}\u200D\u{1F5E8}`))
|
|
453
|
-
];
|
|
454
|
-
this.logger = {
|
|
455
|
-
error: (...messages) => {
|
|
456
|
-
for (const logger of this.loggers) logger.error(...messages);
|
|
457
|
-
},
|
|
458
|
-
info: (...messages) => {
|
|
459
|
-
for (const logger of this.loggers) logger.info(...messages);
|
|
460
|
-
},
|
|
461
|
-
warn: (...messages) => {
|
|
462
|
-
for (const logger of this.loggers) logger.warn(...messages);
|
|
463
|
-
}
|
|
464
|
-
};
|
|
465
|
-
if (store !== null) {
|
|
466
|
-
this.valueMap = new Map(store == null ? void 0 : store.valueMap);
|
|
467
|
-
this.operation = __spreadValues({}, store == null ? void 0 : store.operation);
|
|
468
|
-
if (isRootStore(store)) {
|
|
469
|
-
this.transactionMeta = {
|
|
470
|
-
epoch: new Map(store == null ? void 0 : store.transactionMeta.epoch),
|
|
471
|
-
actionContinuities: new Junction(
|
|
472
|
-
store == null ? void 0 : store.transactionMeta.actionContinuities.toJSON()
|
|
473
|
-
)
|
|
474
|
-
};
|
|
475
|
-
}
|
|
476
|
-
this.config = __spreadValues(__spreadValues({}, store == null ? void 0 : store.config), config);
|
|
477
|
-
for (const [, family] of store.families) {
|
|
478
|
-
family.install(this);
|
|
479
|
-
}
|
|
480
|
-
const mutableHelpers = /* @__PURE__ */ new Set();
|
|
481
|
-
for (const [, atom] of store.atoms) {
|
|
482
|
-
if (mutableHelpers.has(atom.key)) {
|
|
483
|
-
continue;
|
|
484
|
-
}
|
|
485
|
-
atom.install(this);
|
|
486
|
-
if (atom.type === `mutable_atom`) {
|
|
487
|
-
const originalJsonToken = getJsonToken(atom, store);
|
|
488
|
-
const originalUpdateToken = getUpdateToken(atom);
|
|
489
|
-
mutableHelpers.add(originalJsonToken.key);
|
|
490
|
-
mutableHelpers.add(originalUpdateToken.key);
|
|
491
|
-
}
|
|
492
|
-
}
|
|
493
|
-
for (const [, selector] of store.readonlySelectors) {
|
|
494
|
-
selector.install(this);
|
|
495
|
-
}
|
|
496
|
-
for (const [, selector] of store.selectors) {
|
|
497
|
-
if (mutableHelpers.has(selector.key)) {
|
|
498
|
-
continue;
|
|
499
|
-
}
|
|
500
|
-
selector.install(this);
|
|
501
|
-
}
|
|
502
|
-
for (const [, tx] of store.transactions) {
|
|
503
|
-
tx.install(this);
|
|
504
|
-
}
|
|
505
|
-
for (const [, timeline] of store.timelines) {
|
|
506
|
-
timeline.install(this);
|
|
507
|
-
}
|
|
508
|
-
}
|
|
400
|
+
return;
|
|
509
401
|
}
|
|
402
|
+
store.logger.info(
|
|
403
|
+
`\u{1FA82}`,
|
|
404
|
+
`transaction`,
|
|
405
|
+
target.transactionMeta.update.key,
|
|
406
|
+
`Aborting transaction`
|
|
407
|
+
);
|
|
408
|
+
target.parent.child = null;
|
|
510
409
|
};
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
410
|
+
|
|
411
|
+
// internal/src/not-found-error.ts
|
|
412
|
+
var capitalize = (str) => str[0].toUpperCase() + str.slice(1);
|
|
413
|
+
function prettyPrintTokenType(token) {
|
|
414
|
+
switch (token.type) {
|
|
415
|
+
case `atom_family`:
|
|
416
|
+
return `Atom Family`;
|
|
417
|
+
case `molecule_family`:
|
|
418
|
+
return `Molecule Family`;
|
|
419
|
+
case `readonly_selector`:
|
|
420
|
+
return `Readonly Selector`;
|
|
421
|
+
case `readonly_selector_family`:
|
|
422
|
+
return `Readonly Selector Family`;
|
|
423
|
+
case `selector_family`:
|
|
424
|
+
return `Selector Family`;
|
|
425
|
+
default:
|
|
426
|
+
return capitalize(token.type);
|
|
519
427
|
}
|
|
520
|
-
}
|
|
521
|
-
var
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
428
|
+
}
|
|
429
|
+
var NotFoundError = class extends Error {
|
|
430
|
+
constructor(token, store) {
|
|
431
|
+
super(
|
|
432
|
+
`${prettyPrintTokenType(token)} "${token.key}" not found in store "${store.config.name}".`
|
|
433
|
+
);
|
|
525
434
|
}
|
|
526
|
-
Object.assign(store, new Store(config));
|
|
527
|
-
store.config = config;
|
|
528
435
|
};
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
withdrawn = target.atoms.get(token.key);
|
|
537
|
-
break;
|
|
538
|
-
case `selector`:
|
|
539
|
-
withdrawn = target.selectors.get(token.key);
|
|
540
|
-
break;
|
|
541
|
-
case `readonly_selector`:
|
|
542
|
-
withdrawn = target.readonlySelectors.get(token.key);
|
|
543
|
-
break;
|
|
544
|
-
case `atom_family`:
|
|
545
|
-
case `mutable_atom_family`:
|
|
546
|
-
case `selector_family`:
|
|
547
|
-
case `readonly_selector_family`:
|
|
548
|
-
withdrawn = target.families.get(token.key);
|
|
549
|
-
break;
|
|
550
|
-
case `timeline`:
|
|
551
|
-
withdrawn = target.timelines.get(token.key);
|
|
552
|
-
break;
|
|
553
|
-
case `transaction`:
|
|
554
|
-
withdrawn = target.transactions.get(token.key);
|
|
555
|
-
break;
|
|
556
|
-
case `molecule`:
|
|
557
|
-
withdrawn = target.molecules.get(json.stringifyJson(token.key));
|
|
558
|
-
break;
|
|
559
|
-
case `molecule_family`:
|
|
560
|
-
withdrawn = target.moleculeFamilies.get(token.key);
|
|
561
|
-
break;
|
|
562
|
-
}
|
|
563
|
-
if (withdrawn) {
|
|
564
|
-
return withdrawn;
|
|
436
|
+
|
|
437
|
+
// internal/src/transaction/act-upon-store.ts
|
|
438
|
+
function actUponStore(token, id, store) {
|
|
439
|
+
return (...parameters) => {
|
|
440
|
+
const tx = withdraw(token, store);
|
|
441
|
+
if (tx) {
|
|
442
|
+
return tx.run(parameters, id);
|
|
565
443
|
}
|
|
566
|
-
|
|
567
|
-
}
|
|
568
|
-
throw new NotFoundError(token, store);
|
|
444
|
+
throw new NotFoundError(token, store);
|
|
445
|
+
};
|
|
569
446
|
}
|
|
570
447
|
|
|
448
|
+
// internal/src/set-state/become.ts
|
|
449
|
+
var become = (nextVersionOfThing) => (originalThing) => nextVersionOfThing instanceof Function ? nextVersionOfThing(
|
|
450
|
+
originalThing instanceof Function ? originalThing() : originalThing
|
|
451
|
+
) : nextVersionOfThing;
|
|
452
|
+
|
|
571
453
|
// internal/src/get-state/read-or-compute-value.ts
|
|
572
454
|
var readOrComputeValue = (state, target) => {
|
|
573
455
|
if (target.valueMap.has(state.key)) {
|
|
@@ -588,176 +470,6 @@ var readOrComputeValue = (state, target) => {
|
|
|
588
470
|
);
|
|
589
471
|
return state.default instanceof Function ? state.default() : state.default;
|
|
590
472
|
};
|
|
591
|
-
function createRegularAtomFamily(options, store) {
|
|
592
|
-
const subject = new Subject();
|
|
593
|
-
const atomFamily = Object.assign(
|
|
594
|
-
(key) => {
|
|
595
|
-
const subKey = json.stringifyJson(key);
|
|
596
|
-
const family = { key: options.key, subKey };
|
|
597
|
-
const fullKey = `${options.key}(${subKey})`;
|
|
598
|
-
const target = newest(store);
|
|
599
|
-
const def = options.default;
|
|
600
|
-
const individualOptions = {
|
|
601
|
-
key: fullKey,
|
|
602
|
-
default: def instanceof Function ? def(key) : def
|
|
603
|
-
};
|
|
604
|
-
if (options.effects) {
|
|
605
|
-
individualOptions.effects = options.effects(key);
|
|
606
|
-
}
|
|
607
|
-
const token = createRegularAtom(individualOptions, family, target);
|
|
608
|
-
subject.next({ type: `state_creation`, token });
|
|
609
|
-
return token;
|
|
610
|
-
},
|
|
611
|
-
{
|
|
612
|
-
key: options.key,
|
|
613
|
-
type: `atom_family`,
|
|
614
|
-
subject,
|
|
615
|
-
install: (s) => createRegularAtomFamily(options, s)
|
|
616
|
-
}
|
|
617
|
-
);
|
|
618
|
-
store.families.set(options.key, atomFamily);
|
|
619
|
-
return atomFamily;
|
|
620
|
-
}
|
|
621
|
-
|
|
622
|
-
// internal/src/families/create-atom-family.ts
|
|
623
|
-
function createAtomFamily(options, store) {
|
|
624
|
-
const isMutable2 = `mutable` in options;
|
|
625
|
-
if (isMutable2) {
|
|
626
|
-
return createMutableAtomFamily(options, store);
|
|
627
|
-
}
|
|
628
|
-
return createRegularAtomFamily(options, store);
|
|
629
|
-
}
|
|
630
|
-
function createReadonlySelectorFamily(options, store) {
|
|
631
|
-
const subject = new Subject();
|
|
632
|
-
const readonlySelectorFamily = Object.assign(
|
|
633
|
-
(key) => {
|
|
634
|
-
const subKey = json.stringifyJson(key);
|
|
635
|
-
const family = { key: options.key, subKey };
|
|
636
|
-
const fullKey = `${options.key}(${subKey})`;
|
|
637
|
-
const target = newest(store);
|
|
638
|
-
const token = createReadonlySelector(
|
|
639
|
-
{
|
|
640
|
-
key: fullKey,
|
|
641
|
-
get: options.get(key)
|
|
642
|
-
},
|
|
643
|
-
family,
|
|
644
|
-
target
|
|
645
|
-
);
|
|
646
|
-
subject.next({ type: `state_creation`, token });
|
|
647
|
-
return token;
|
|
648
|
-
},
|
|
649
|
-
{
|
|
650
|
-
key: options.key,
|
|
651
|
-
type: `readonly_selector_family`,
|
|
652
|
-
subject,
|
|
653
|
-
install: (s) => createReadonlySelectorFamily(options, s)
|
|
654
|
-
}
|
|
655
|
-
);
|
|
656
|
-
store.families.set(options.key, readonlySelectorFamily);
|
|
657
|
-
return readonlySelectorFamily;
|
|
658
|
-
}
|
|
659
|
-
function createWritableSelectorFamily(options, store) {
|
|
660
|
-
const subject = new Subject();
|
|
661
|
-
const selectorFamily = Object.assign(
|
|
662
|
-
(key) => {
|
|
663
|
-
const subKey = json.stringifyJson(key);
|
|
664
|
-
const family = { key: options.key, subKey };
|
|
665
|
-
const fullKey = `${options.key}(${subKey})`;
|
|
666
|
-
const target = newest(store);
|
|
667
|
-
const token = createWritableSelector(
|
|
668
|
-
{
|
|
669
|
-
key: fullKey,
|
|
670
|
-
get: options.get(key),
|
|
671
|
-
set: options.set(key)
|
|
672
|
-
},
|
|
673
|
-
family,
|
|
674
|
-
target
|
|
675
|
-
);
|
|
676
|
-
subject.next({ type: `state_creation`, token });
|
|
677
|
-
return token;
|
|
678
|
-
},
|
|
679
|
-
{
|
|
680
|
-
key: options.key,
|
|
681
|
-
type: `selector_family`,
|
|
682
|
-
subject,
|
|
683
|
-
install: (s) => createWritableSelectorFamily(options, s)
|
|
684
|
-
}
|
|
685
|
-
);
|
|
686
|
-
store.families.set(options.key, selectorFamily);
|
|
687
|
-
return selectorFamily;
|
|
688
|
-
}
|
|
689
|
-
|
|
690
|
-
// internal/src/families/create-selector-family.ts
|
|
691
|
-
function createSelectorFamily(options, store) {
|
|
692
|
-
const isWritable = `set` in options;
|
|
693
|
-
if (isWritable) {
|
|
694
|
-
return createWritableSelectorFamily(options, store);
|
|
695
|
-
}
|
|
696
|
-
return createReadonlySelectorFamily(options, store);
|
|
697
|
-
}
|
|
698
|
-
|
|
699
|
-
// internal/src/transaction/abort-transaction.ts
|
|
700
|
-
var abortTransaction = (store) => {
|
|
701
|
-
const target = newest(store);
|
|
702
|
-
if (!isChildStore(target)) {
|
|
703
|
-
store.logger.warn(
|
|
704
|
-
`\u{1F41E}`,
|
|
705
|
-
`transaction`,
|
|
706
|
-
`???`,
|
|
707
|
-
`abortTransaction called outside of a transaction. This is probably a bug in AtomIO.`
|
|
708
|
-
);
|
|
709
|
-
return;
|
|
710
|
-
}
|
|
711
|
-
store.logger.info(
|
|
712
|
-
`\u{1FA82}`,
|
|
713
|
-
`transaction`,
|
|
714
|
-
target.transactionMeta.update.key,
|
|
715
|
-
`Aborting transaction`
|
|
716
|
-
);
|
|
717
|
-
target.parent.child = null;
|
|
718
|
-
};
|
|
719
|
-
|
|
720
|
-
// internal/src/not-found-error.ts
|
|
721
|
-
var capitalize = (str) => str[0].toUpperCase() + str.slice(1);
|
|
722
|
-
function prettyPrintTokenType(token) {
|
|
723
|
-
switch (token.type) {
|
|
724
|
-
case `atom_family`:
|
|
725
|
-
return `Atom Family`;
|
|
726
|
-
case `molecule_family`:
|
|
727
|
-
return `Molecule Family`;
|
|
728
|
-
case `readonly_selector`:
|
|
729
|
-
return `Readonly Selector`;
|
|
730
|
-
case `readonly_selector_family`:
|
|
731
|
-
return `Readonly Selector Family`;
|
|
732
|
-
case `selector_family`:
|
|
733
|
-
return `Selector Family`;
|
|
734
|
-
default:
|
|
735
|
-
return capitalize(token.type);
|
|
736
|
-
}
|
|
737
|
-
}
|
|
738
|
-
var NotFoundError = class extends Error {
|
|
739
|
-
constructor(token, store) {
|
|
740
|
-
super(
|
|
741
|
-
`${prettyPrintTokenType(token)} "${token.key}" not found in store "${store.config.name}".`
|
|
742
|
-
);
|
|
743
|
-
}
|
|
744
|
-
};
|
|
745
|
-
|
|
746
|
-
// internal/src/transaction/act-upon-store.ts
|
|
747
|
-
function actUponStore(token, id, store) {
|
|
748
|
-
return (...parameters) => {
|
|
749
|
-
const tx = withdraw(token, store);
|
|
750
|
-
if (tx) {
|
|
751
|
-
return tx.run(parameters, id);
|
|
752
|
-
}
|
|
753
|
-
throw new NotFoundError(token, store);
|
|
754
|
-
};
|
|
755
|
-
}
|
|
756
|
-
|
|
757
|
-
// internal/src/set-state/become.ts
|
|
758
|
-
var become = (nextVersionOfThing) => (originalThing) => nextVersionOfThing instanceof Function ? nextVersionOfThing(
|
|
759
|
-
originalThing instanceof Function ? originalThing() : originalThing
|
|
760
|
-
) : nextVersionOfThing;
|
|
761
473
|
|
|
762
474
|
// internal/src/operation.ts
|
|
763
475
|
var openOperation = (token, store) => {
|
|
@@ -854,8 +566,9 @@ var emitUpdate = (state, update, store) => {
|
|
|
854
566
|
|
|
855
567
|
// internal/src/set-state/evict-downstream.ts
|
|
856
568
|
var evictDownStream = (atom, store) => {
|
|
857
|
-
const
|
|
858
|
-
|
|
569
|
+
const target = newest(store);
|
|
570
|
+
const downstreamKeys = target.selectorAtoms.getRelatedKeys(atom.key);
|
|
571
|
+
target.logger.info(
|
|
859
572
|
`\u{1F9F9}`,
|
|
860
573
|
atom.type,
|
|
861
574
|
atom.key,
|
|
@@ -863,20 +576,20 @@ var evictDownStream = (atom, store) => {
|
|
|
863
576
|
downstreamKeys != null ? downstreamKeys : `to evict`
|
|
864
577
|
);
|
|
865
578
|
if (downstreamKeys) {
|
|
866
|
-
if (
|
|
867
|
-
|
|
579
|
+
if (target.operation.open) {
|
|
580
|
+
target.logger.info(
|
|
868
581
|
`\u{1F9F9}`,
|
|
869
582
|
atom.type,
|
|
870
583
|
atom.key,
|
|
871
|
-
`[ ${[...
|
|
584
|
+
`[ ${[...target.operation.done].join(`, `)} ] already done`
|
|
872
585
|
);
|
|
873
586
|
}
|
|
874
587
|
for (const key of downstreamKeys) {
|
|
875
|
-
if (isDone(key,
|
|
588
|
+
if (isDone(key, target)) {
|
|
876
589
|
continue;
|
|
877
590
|
}
|
|
878
|
-
evictCachedValue(key,
|
|
879
|
-
markDone(key,
|
|
591
|
+
evictCachedValue(key, target);
|
|
592
|
+
markDone(key, target);
|
|
880
593
|
}
|
|
881
594
|
}
|
|
882
595
|
};
|
|
@@ -1012,582 +725,463 @@ function ingestAtomUpdate(applying, atomUpdate, store) {
|
|
|
1012
725
|
}
|
|
1013
726
|
setIntoStore(token, value, store);
|
|
1014
727
|
}
|
|
1015
|
-
|
|
1016
|
-
// internal/src/molecule/create-molecule-family.ts
|
|
1017
|
-
function createMoleculeFamily(options, store) {
|
|
1018
|
-
var _a;
|
|
728
|
+
function createRegularAtomFamily(options, store) {
|
|
1019
729
|
const subject = new Subject();
|
|
1020
|
-
const
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
730
|
+
const atomFamily = Object.assign(
|
|
731
|
+
(key) => {
|
|
732
|
+
const subKey = json.stringifyJson(key);
|
|
733
|
+
const family = { key: options.key, subKey };
|
|
734
|
+
const fullKey = `${options.key}(${subKey})`;
|
|
735
|
+
const target = newest(store);
|
|
736
|
+
const def = options.default;
|
|
737
|
+
const individualOptions = {
|
|
738
|
+
key: fullKey,
|
|
739
|
+
default: def instanceof Function ? def(key) : def
|
|
740
|
+
};
|
|
741
|
+
if (options.effects) {
|
|
742
|
+
individualOptions.effects = options.effects(key);
|
|
743
|
+
}
|
|
744
|
+
const token = createRegularAtom(individualOptions, family, target);
|
|
745
|
+
subject.next({ type: `state_creation`, token });
|
|
746
|
+
return token;
|
|
747
|
+
},
|
|
748
|
+
{
|
|
749
|
+
key: options.key,
|
|
750
|
+
type: `atom_family`,
|
|
751
|
+
subject,
|
|
752
|
+
install: (s) => createRegularAtomFamily(options, s)
|
|
753
|
+
}
|
|
754
|
+
);
|
|
755
|
+
store.families.set(options.key, atomFamily);
|
|
756
|
+
return atomFamily;
|
|
1031
757
|
}
|
|
1032
758
|
|
|
1033
|
-
// internal/src/
|
|
1034
|
-
function
|
|
1035
|
-
const
|
|
1036
|
-
|
|
1037
|
-
|
|
1038
|
-
if (isTransaction) {
|
|
1039
|
-
store.transactionMeta.update.updates.push({
|
|
1040
|
-
type: `state_creation`,
|
|
1041
|
-
token: stateToken
|
|
1042
|
-
});
|
|
1043
|
-
} else {
|
|
1044
|
-
molecule.subject.next({ type: `state_creation`, token: stateToken });
|
|
759
|
+
// internal/src/families/create-atom-family.ts
|
|
760
|
+
function createAtomFamily(options, store) {
|
|
761
|
+
const isMutable2 = `mutable` in options;
|
|
762
|
+
if (isMutable2) {
|
|
763
|
+
return createMutableAtomFamily(options, store);
|
|
1045
764
|
}
|
|
1046
|
-
return
|
|
765
|
+
return createRegularAtomFamily(options, store);
|
|
1047
766
|
}
|
|
1048
767
|
|
|
1049
|
-
// internal/src/
|
|
1050
|
-
|
|
1051
|
-
|
|
1052
|
-
|
|
1053
|
-
|
|
1054
|
-
}
|
|
768
|
+
// internal/src/keys.ts
|
|
769
|
+
var isAtomKey = (key, store) => newest(store).atoms.has(key);
|
|
770
|
+
var isSelectorKey = (key, store) => newest(store).selectors.has(key);
|
|
771
|
+
var isReadonlySelectorKey = (key, store) => newest(store).readonlySelectors.has(key);
|
|
772
|
+
var isStateKey = (key, store) => isAtomKey(key, store) || isSelectorKey(key, store) || isReadonlySelectorKey(key, store);
|
|
1055
773
|
|
|
1056
|
-
// internal/src/
|
|
1057
|
-
|
|
1058
|
-
|
|
1059
|
-
|
|
1060
|
-
const molecule = withdraw(token, store);
|
|
1061
|
-
return molecule.instance;
|
|
1062
|
-
} catch (_) {
|
|
1063
|
-
return void 0;
|
|
1064
|
-
}
|
|
1065
|
-
}
|
|
1066
|
-
const state = withdraw(token, store);
|
|
1067
|
-
return readOrComputeValue(state, store);
|
|
1068
|
-
}
|
|
1069
|
-
var Molecule = class {
|
|
1070
|
-
constructor(ctx, key, family) {
|
|
1071
|
-
this.key = key;
|
|
1072
|
-
this.type = `molecule`;
|
|
1073
|
-
this.subject = new Subject();
|
|
1074
|
-
this.tokens = /* @__PURE__ */ new Map();
|
|
1075
|
-
this.above = /* @__PURE__ */ new Map();
|
|
1076
|
-
this.below = /* @__PURE__ */ new Map();
|
|
1077
|
-
this.joins = /* @__PURE__ */ new Map();
|
|
1078
|
-
this.stringKey = json.stringifyJson(key);
|
|
1079
|
-
if (family) {
|
|
1080
|
-
this.family = family;
|
|
1081
|
-
}
|
|
1082
|
-
if (ctx) {
|
|
1083
|
-
if (Array.isArray(ctx)) {
|
|
1084
|
-
for (const molecule of ctx) {
|
|
1085
|
-
this.above.set(molecule.stringKey, molecule);
|
|
1086
|
-
}
|
|
1087
|
-
} else {
|
|
1088
|
-
this.above.set(ctx.stringKey, ctx);
|
|
1089
|
-
}
|
|
1090
|
-
}
|
|
1091
|
-
}
|
|
774
|
+
// internal/src/selector/get-selector-dependency-keys.ts
|
|
775
|
+
var getSelectorDependencyKeys = (key, store) => {
|
|
776
|
+
const sources = newest(store).selectorGraph.getRelationEntries({ downstreamSelectorKey: key }).filter(([_, { source }]) => source !== key).map(([_, { source }]) => source).filter((source) => isStateKey(source, store));
|
|
777
|
+
return sources;
|
|
1092
778
|
};
|
|
1093
779
|
|
|
1094
|
-
// internal/src/
|
|
1095
|
-
|
|
1096
|
-
const
|
|
1097
|
-
const
|
|
1098
|
-
|
|
1099
|
-
|
|
1100
|
-
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
|
|
1106
|
-
}
|
|
1107
|
-
const stringKey = json.stringifyJson(ctx.key);
|
|
1108
|
-
const molecule2 = store.molecules.get(stringKey);
|
|
1109
|
-
if (!molecule2) {
|
|
780
|
+
// internal/src/selector/trace-selector-atoms.ts
|
|
781
|
+
var traceSelectorAtoms = (selectorKey, directDependencyKey, store) => {
|
|
782
|
+
const rootKeys = [];
|
|
783
|
+
const indirectDependencyKeys = getSelectorDependencyKeys(
|
|
784
|
+
directDependencyKey,
|
|
785
|
+
store
|
|
786
|
+
);
|
|
787
|
+
let depth = 0;
|
|
788
|
+
while (indirectDependencyKeys.length > 0) {
|
|
789
|
+
const indirectDependencyKey = indirectDependencyKeys.shift();
|
|
790
|
+
++depth;
|
|
791
|
+
if (depth > 99999) {
|
|
1110
792
|
throw new Error(
|
|
1111
|
-
`
|
|
793
|
+
`Maximum selector dependency depth exceeded (> 99999) in selector "${selectorKey}". This is likely due to a circular dependency.`
|
|
1112
794
|
);
|
|
1113
795
|
}
|
|
1114
|
-
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
|
|
1118
|
-
|
|
1119
|
-
|
|
1120
|
-
|
|
796
|
+
if (!isAtomKey(indirectDependencyKey, store)) {
|
|
797
|
+
indirectDependencyKeys.push(
|
|
798
|
+
...getSelectorDependencyKeys(indirectDependencyKey, store)
|
|
799
|
+
);
|
|
800
|
+
} else if (!rootKeys.includes(indirectDependencyKey)) {
|
|
801
|
+
rootKeys.push(indirectDependencyKey);
|
|
802
|
+
}
|
|
1121
803
|
}
|
|
1122
|
-
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
)
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
804
|
+
return rootKeys;
|
|
805
|
+
};
|
|
806
|
+
var traceAllSelectorAtoms = (selector, store) => {
|
|
807
|
+
const selectorKey = selector.key;
|
|
808
|
+
const directDependencyKeys = getSelectorDependencyKeys(selectorKey, store);
|
|
809
|
+
return directDependencyKeys.flatMap(
|
|
810
|
+
(depKey) => isAtomKey(depKey, store) ? depKey : traceSelectorAtoms(selectorKey, depKey, store)
|
|
811
|
+
);
|
|
812
|
+
};
|
|
813
|
+
|
|
814
|
+
// internal/src/selector/update-selector-atoms.ts
|
|
815
|
+
var updateSelectorAtoms = (selectorKey, dependency, store) => {
|
|
816
|
+
const target = newest(store);
|
|
817
|
+
if (dependency.type === `atom` || dependency.type === `mutable_atom`) {
|
|
818
|
+
target.selectorAtoms.set({
|
|
819
|
+
selectorKey,
|
|
820
|
+
atomKey: dependency.key
|
|
821
|
+
});
|
|
822
|
+
store.logger.info(
|
|
823
|
+
`\u{1F50D}`,
|
|
824
|
+
`selector`,
|
|
825
|
+
selectorKey,
|
|
826
|
+
`discovers root atom "${dependency.key}"`
|
|
827
|
+
);
|
|
828
|
+
} else {
|
|
829
|
+
const rootKeys = traceSelectorAtoms(selectorKey, dependency.key, store);
|
|
830
|
+
store.logger.info(
|
|
831
|
+
`\u{1F50D}`,
|
|
832
|
+
`selector`,
|
|
833
|
+
selectorKey,
|
|
834
|
+
`discovers root atoms: [ ${rootKeys.map((key) => `"${key}"`).join(`, `)} ]`
|
|
835
|
+
);
|
|
836
|
+
for (const atomKey of rootKeys) {
|
|
837
|
+
target.selectorAtoms = target.selectorAtoms.set({
|
|
838
|
+
selectorKey,
|
|
839
|
+
atomKey
|
|
840
|
+
});
|
|
841
|
+
}
|
|
842
|
+
}
|
|
843
|
+
};
|
|
844
|
+
|
|
845
|
+
// internal/src/selector/register-selector.ts
|
|
846
|
+
var registerSelector = (selectorKey, store) => ({
|
|
847
|
+
get: (dependency) => {
|
|
848
|
+
const target = newest(store);
|
|
849
|
+
const dependencyState = withdraw(dependency, store);
|
|
850
|
+
const dependencyValue = readOrComputeValue(dependencyState, store);
|
|
851
|
+
store.logger.info(
|
|
852
|
+
`\u{1F50C}`,
|
|
853
|
+
`selector`,
|
|
854
|
+
selectorKey,
|
|
855
|
+
`registers dependency ( "${dependency.key}" =`,
|
|
856
|
+
dependencyValue,
|
|
857
|
+
`)`
|
|
858
|
+
);
|
|
859
|
+
target.selectorGraph.set(
|
|
860
|
+
{
|
|
861
|
+
upstreamSelectorKey: dependency.key,
|
|
862
|
+
downstreamSelectorKey: selectorKey
|
|
863
|
+
},
|
|
864
|
+
{
|
|
865
|
+
source: dependency.key
|
|
1155
866
|
}
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1163
|
-
|
|
1164
|
-
|
|
1165
|
-
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
|
|
867
|
+
);
|
|
868
|
+
updateSelectorAtoms(selectorKey, dependency, store);
|
|
869
|
+
return dependencyValue;
|
|
870
|
+
},
|
|
871
|
+
set: (WritableToken, newValue) => {
|
|
872
|
+
const target = newest(store);
|
|
873
|
+
const state = withdraw(WritableToken, target);
|
|
874
|
+
setAtomOrSelector(state, newValue, target);
|
|
875
|
+
},
|
|
876
|
+
find: (token, key) => findInStore(token, key, store),
|
|
877
|
+
seek: (token, key) => seekInStore(token, key, store),
|
|
878
|
+
json: (token) => getJsonToken(token, store)
|
|
879
|
+
});
|
|
880
|
+
|
|
881
|
+
// internal/src/selector/create-readonly-selector.ts
|
|
882
|
+
var createReadonlySelector = (options, family, store) => {
|
|
883
|
+
const target = newest(store);
|
|
884
|
+
const subject = new Subject();
|
|
885
|
+
const { get, find, seek, json } = registerSelector(options.key, target);
|
|
886
|
+
const getSelf = () => {
|
|
887
|
+
const value = options.get({ get, find, seek, json });
|
|
888
|
+
cacheValue(options.key, value, subject, newest(store));
|
|
889
|
+
return value;
|
|
1170
890
|
};
|
|
1171
|
-
const
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1176
|
-
|
|
1177
|
-
|
|
1178
|
-
|
|
891
|
+
const readonlySelector = __spreadValues(__spreadProps(__spreadValues({}, options), {
|
|
892
|
+
subject,
|
|
893
|
+
install: (s) => createReadonlySelector(options, family, s),
|
|
894
|
+
get: getSelf,
|
|
895
|
+
type: `readonly_selector`
|
|
896
|
+
}), family && { family });
|
|
897
|
+
target.readonlySelectors.set(options.key, readonlySelector);
|
|
898
|
+
const initialValue = getSelf();
|
|
899
|
+
store.logger.info(
|
|
900
|
+
`\u2728`,
|
|
901
|
+
readonlySelector.type,
|
|
902
|
+
readonlySelector.key,
|
|
903
|
+
`=`,
|
|
904
|
+
initialValue
|
|
905
|
+
);
|
|
906
|
+
const token = {
|
|
907
|
+
key: options.key,
|
|
908
|
+
type: `readonly_selector`
|
|
1179
909
|
};
|
|
1180
|
-
|
|
1181
|
-
|
|
1182
|
-
target.transactionMeta.update.updates.push(update);
|
|
1183
|
-
} else {
|
|
1184
|
-
family.subject.next(update);
|
|
910
|
+
if (family) {
|
|
911
|
+
token.family = family;
|
|
1185
912
|
}
|
|
1186
913
|
return token;
|
|
1187
|
-
}
|
|
914
|
+
};
|
|
1188
915
|
|
|
1189
|
-
// internal/src/
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
916
|
+
// internal/src/selector/create-writable-selector.ts
|
|
917
|
+
var createWritableSelector = (options, family, store) => {
|
|
918
|
+
const target = newest(store);
|
|
919
|
+
const subject = new Subject();
|
|
920
|
+
const transactors = registerSelector(options.key, target);
|
|
921
|
+
const { find, get, seek, json } = transactors;
|
|
922
|
+
const readonlyTransactors = { find, get, seek, json };
|
|
923
|
+
const getSelf = (innerTarget = newest(store)) => {
|
|
924
|
+
const value = options.get(readonlyTransactors);
|
|
925
|
+
cacheValue(options.key, value, subject, innerTarget);
|
|
926
|
+
return value;
|
|
927
|
+
};
|
|
928
|
+
const setSelf = (next) => {
|
|
929
|
+
const innerTarget = newest(store);
|
|
930
|
+
const oldValue = getSelf(innerTarget);
|
|
931
|
+
const newValue = become(next)(oldValue);
|
|
932
|
+
store.logger.info(
|
|
933
|
+
`\u{1F4DD}`,
|
|
934
|
+
`selector`,
|
|
935
|
+
options.key,
|
|
936
|
+
`set (`,
|
|
937
|
+
oldValue,
|
|
938
|
+
`->`,
|
|
939
|
+
newValue,
|
|
940
|
+
`)`
|
|
941
|
+
);
|
|
942
|
+
cacheValue(options.key, newValue, subject, innerTarget);
|
|
943
|
+
markDone(options.key, innerTarget);
|
|
944
|
+
if (isRootStore(innerTarget)) {
|
|
945
|
+
subject.next({ newValue, oldValue });
|
|
1199
946
|
}
|
|
947
|
+
options.set(transactors, newValue);
|
|
948
|
+
};
|
|
949
|
+
const mySelector = __spreadValues(__spreadProps(__spreadValues({}, options), {
|
|
950
|
+
subject,
|
|
951
|
+
install: (s) => createWritableSelector(options, family, s),
|
|
952
|
+
get: getSelf,
|
|
953
|
+
set: setSelf,
|
|
954
|
+
type: `selector`
|
|
955
|
+
}), family && { family });
|
|
956
|
+
target.selectors.set(options.key, mySelector);
|
|
957
|
+
const initialValue = getSelf();
|
|
958
|
+
store.logger.info(`\u2728`, mySelector.type, mySelector.key, `=`, initialValue);
|
|
959
|
+
const token = {
|
|
960
|
+
key: options.key,
|
|
961
|
+
type: `selector`
|
|
962
|
+
};
|
|
963
|
+
if (family) {
|
|
964
|
+
token.family = family;
|
|
1200
965
|
}
|
|
1201
|
-
|
|
1202
|
-
|
|
1203
|
-
|
|
1204
|
-
|
|
1205
|
-
|
|
1206
|
-
|
|
1207
|
-
|
|
1208
|
-
|
|
1209
|
-
|
|
1210
|
-
|
|
1211
|
-
break;
|
|
1212
|
-
}
|
|
966
|
+
return token;
|
|
967
|
+
};
|
|
968
|
+
|
|
969
|
+
// internal/src/selector/create-standalone-selector.ts
|
|
970
|
+
function createStandaloneSelector(options, store) {
|
|
971
|
+
const isWritable = `set` in options;
|
|
972
|
+
if (isWritable) {
|
|
973
|
+
const state2 = createWritableSelector(options, void 0, store);
|
|
974
|
+
store.on.selectorCreation.next(state2);
|
|
975
|
+
return state2;
|
|
1213
976
|
}
|
|
977
|
+
const state = createReadonlySelector(options, void 0, store);
|
|
978
|
+
store.on.selectorCreation.next(state);
|
|
979
|
+
return state;
|
|
1214
980
|
}
|
|
1215
|
-
|
|
1216
|
-
|
|
1217
|
-
|
|
1218
|
-
|
|
1219
|
-
|
|
1220
|
-
|
|
1221
|
-
|
|
1222
|
-
|
|
981
|
+
|
|
982
|
+
// internal/src/selector/dispose-selector.ts
|
|
983
|
+
function disposeSelector(selectorToken, store) {
|
|
984
|
+
var _a;
|
|
985
|
+
const target = newest(store);
|
|
986
|
+
const { key } = selectorToken;
|
|
987
|
+
const selector = (_a = target.selectors.get(key)) != null ? _a : target.readonlySelectors.get(key);
|
|
988
|
+
if (!selector) {
|
|
989
|
+
store.logger.info(
|
|
990
|
+
`\u274C`,
|
|
991
|
+
`selector`,
|
|
992
|
+
key,
|
|
993
|
+
`Tried to dispose selector, but it does not exist in the store.`
|
|
994
|
+
);
|
|
995
|
+
} else if (!selector.family) {
|
|
996
|
+
store.logger.error(
|
|
997
|
+
`\u274C`,
|
|
998
|
+
`selector`,
|
|
999
|
+
key,
|
|
1000
|
+
`Standalone selectors cannot be disposed.`
|
|
1001
|
+
);
|
|
1002
|
+
} else {
|
|
1003
|
+
const molecule = target.molecules.get(selector.family.subKey);
|
|
1004
|
+
if (molecule) {
|
|
1005
|
+
molecule.tokens.delete(key);
|
|
1006
|
+
}
|
|
1007
|
+
switch (selectorToken.type) {
|
|
1008
|
+
case `selector`:
|
|
1009
|
+
{
|
|
1010
|
+
target.selectors.delete(key);
|
|
1011
|
+
const family = withdraw(
|
|
1012
|
+
{ key: selector.family.key, type: `selector_family` },
|
|
1013
|
+
store
|
|
1014
|
+
);
|
|
1015
|
+
family.subject.next({
|
|
1016
|
+
type: `state_disposal`,
|
|
1017
|
+
token: selectorToken
|
|
1018
|
+
});
|
|
1019
|
+
}
|
|
1020
|
+
break;
|
|
1021
|
+
case `readonly_selector`:
|
|
1022
|
+
{
|
|
1023
|
+
target.readonlySelectors.delete(key);
|
|
1024
|
+
const family = withdraw(
|
|
1025
|
+
{ key: selector.family.key, type: `readonly_selector_family` },
|
|
1026
|
+
store
|
|
1027
|
+
);
|
|
1028
|
+
family.subject.next({
|
|
1029
|
+
type: `state_disposal`,
|
|
1030
|
+
token: selectorToken
|
|
1031
|
+
});
|
|
1032
|
+
}
|
|
1033
|
+
break;
|
|
1034
|
+
}
|
|
1035
|
+
target.valueMap.delete(key);
|
|
1036
|
+
target.selectorAtoms.delete(key);
|
|
1037
|
+
const downstreamTokens = target.selectorGraph.getRelationEntries({ upstreamSelectorKey: key }).filter(([_, { source }]) => source === key).map(
|
|
1038
|
+
([downstreamSelectorKey]) => {
|
|
1039
|
+
var _a2;
|
|
1040
|
+
return (_a2 = target.selectors.get(downstreamSelectorKey)) != null ? _a2 : target.readonlySelectors.get(downstreamSelectorKey);
|
|
1223
1041
|
}
|
|
1224
|
-
|
|
1225
|
-
|
|
1042
|
+
);
|
|
1043
|
+
for (const downstreamToken of downstreamTokens) {
|
|
1044
|
+
if (downstreamToken) {
|
|
1045
|
+
disposeSelector(downstreamToken, store);
|
|
1226
1046
|
}
|
|
1227
|
-
|
|
1047
|
+
}
|
|
1048
|
+
target.selectorGraph.delete(key);
|
|
1049
|
+
store.logger.info(`\u{1F525}`, selectorToken.type, key, `deleted`);
|
|
1050
|
+
if (isChildStore(target) && target.transactionMeta.phase === `building`) {
|
|
1051
|
+
target.transactionMeta.update.updates.push({
|
|
1052
|
+
type: `state_disposal`,
|
|
1053
|
+
token: selectorToken
|
|
1054
|
+
});
|
|
1055
|
+
} else {
|
|
1056
|
+
store.on.selectorDisposal.next(selectorToken);
|
|
1228
1057
|
}
|
|
1229
1058
|
}
|
|
1230
1059
|
}
|
|
1231
|
-
|
|
1232
|
-
|
|
1233
|
-
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1060
|
+
|
|
1061
|
+
// internal/src/families/create-readonly-selector-family.ts
|
|
1062
|
+
function createReadonlySelectorFamily(options, store) {
|
|
1063
|
+
const subject = new Subject();
|
|
1064
|
+
const readonlySelectorFamily = Object.assign(
|
|
1065
|
+
(key) => {
|
|
1066
|
+
const subKey = json.stringifyJson(key);
|
|
1067
|
+
const family = { key: options.key, subKey };
|
|
1068
|
+
const fullKey = `${options.key}(${subKey})`;
|
|
1069
|
+
const target = newest(store);
|
|
1070
|
+
const token = createReadonlySelector(
|
|
1071
|
+
{
|
|
1072
|
+
key: fullKey,
|
|
1073
|
+
get: options.get(key)
|
|
1074
|
+
},
|
|
1075
|
+
family,
|
|
1076
|
+
target
|
|
1240
1077
|
);
|
|
1241
|
-
|
|
1242
|
-
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
|
|
1078
|
+
subject.next({ type: `state_creation`, token });
|
|
1079
|
+
return token;
|
|
1080
|
+
},
|
|
1081
|
+
{
|
|
1082
|
+
key: options.key,
|
|
1083
|
+
type: `readonly_selector_family`,
|
|
1084
|
+
subject,
|
|
1085
|
+
install: (s) => createReadonlySelectorFamily(options, s)
|
|
1086
|
+
}
|
|
1087
|
+
);
|
|
1088
|
+
store.families.set(options.key, readonlySelectorFamily);
|
|
1089
|
+
return readonlySelectorFamily;
|
|
1246
1090
|
}
|
|
1247
|
-
function
|
|
1248
|
-
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
|
|
1091
|
+
function createWritableSelectorFamily(options, store) {
|
|
1092
|
+
const subject = new Subject();
|
|
1093
|
+
const selectorFamily = Object.assign(
|
|
1094
|
+
(key) => {
|
|
1095
|
+
const subKey = json.stringifyJson(key);
|
|
1096
|
+
const family = { key: options.key, subKey };
|
|
1097
|
+
const fullKey = `${options.key}(${subKey})`;
|
|
1098
|
+
const target = newest(store);
|
|
1099
|
+
const token = createWritableSelector(
|
|
1100
|
+
{
|
|
1101
|
+
key: fullKey,
|
|
1102
|
+
get: options.get(key),
|
|
1103
|
+
set: options.set(key)
|
|
1104
|
+
},
|
|
1105
|
+
family,
|
|
1106
|
+
target
|
|
1258
1107
|
);
|
|
1259
|
-
|
|
1260
|
-
|
|
1108
|
+
subject.next({ type: `state_creation`, token });
|
|
1109
|
+
return token;
|
|
1110
|
+
},
|
|
1111
|
+
{
|
|
1112
|
+
key: options.key,
|
|
1113
|
+
type: `selector_family`,
|
|
1114
|
+
subject,
|
|
1115
|
+
install: (s) => createWritableSelectorFamily(options, s)
|
|
1116
|
+
}
|
|
1117
|
+
);
|
|
1118
|
+
store.families.set(options.key, selectorFamily);
|
|
1119
|
+
return selectorFamily;
|
|
1261
1120
|
}
|
|
1262
1121
|
|
|
1263
|
-
// internal/src/
|
|
1264
|
-
function
|
|
1265
|
-
const
|
|
1266
|
-
|
|
1267
|
-
|
|
1122
|
+
// internal/src/families/create-selector-family.ts
|
|
1123
|
+
function createSelectorFamily(options, store) {
|
|
1124
|
+
const isWritable = `set` in options;
|
|
1125
|
+
if (isWritable) {
|
|
1126
|
+
return createWritableSelectorFamily(options, store);
|
|
1268
1127
|
}
|
|
1128
|
+
return createReadonlySelectorFamily(options, store);
|
|
1269
1129
|
}
|
|
1270
1130
|
|
|
1271
|
-
// internal/src/
|
|
1272
|
-
function
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
|
|
1282
|
-
|
|
1283
|
-
|
|
1284
|
-
|
|
1285
|
-
|
|
1286
|
-
case `molecule_creation`:
|
|
1287
|
-
ingestMoleculeCreationEvent(updateFromTransaction, applying, store);
|
|
1288
|
-
break;
|
|
1289
|
-
case `molecule_disposal`:
|
|
1290
|
-
ingestMoleculeDisposalEvent(updateFromTransaction, applying, store);
|
|
1291
|
-
break;
|
|
1292
|
-
case `transaction_update`:
|
|
1293
|
-
ingestTransactionUpdate(applying, updateFromTransaction, store);
|
|
1294
|
-
break;
|
|
1131
|
+
// internal/src/molecule/dispose-molecule.ts
|
|
1132
|
+
function disposeMolecule(token, store) {
|
|
1133
|
+
var _a;
|
|
1134
|
+
let molecule;
|
|
1135
|
+
try {
|
|
1136
|
+
molecule = withdraw(token, store);
|
|
1137
|
+
} catch (thrown) {
|
|
1138
|
+
if (thrown instanceof Error) {
|
|
1139
|
+
store.logger.error(
|
|
1140
|
+
`\u{1F41E}`,
|
|
1141
|
+
`molecule`,
|
|
1142
|
+
JSON.stringify(token.key),
|
|
1143
|
+
`Failed to dispose molecule, because it was not found in the store.`,
|
|
1144
|
+
thrown.message
|
|
1145
|
+
);
|
|
1295
1146
|
}
|
|
1296
|
-
}
|
|
1297
|
-
}
|
|
1298
|
-
|
|
1299
|
-
// internal/src/transaction/set-epoch-number.ts
|
|
1300
|
-
function setEpochNumberOfContinuity(continuityKey, newEpoch, store) {
|
|
1301
|
-
const isRoot = isRootStore(store);
|
|
1302
|
-
if (isRoot && continuityKey) {
|
|
1303
|
-
store.transactionMeta.epoch.set(continuityKey, newEpoch);
|
|
1304
|
-
}
|
|
1305
|
-
}
|
|
1306
|
-
function setEpochNumberOfAction(transactionKey, newEpoch, store) {
|
|
1307
|
-
const isRoot = isRootStore(store);
|
|
1308
|
-
if (!isRoot) {
|
|
1309
1147
|
return;
|
|
1310
1148
|
}
|
|
1311
|
-
const
|
|
1312
|
-
|
|
1313
|
-
|
|
1149
|
+
const { family } = token;
|
|
1150
|
+
const context = [];
|
|
1151
|
+
for (const above of molecule.above.values()) {
|
|
1152
|
+
context.push(deposit(above));
|
|
1314
1153
|
}
|
|
1315
|
-
|
|
1316
|
-
|
|
1317
|
-
|
|
1318
|
-
|
|
1319
|
-
var _a;
|
|
1320
|
-
const child = newest(store);
|
|
1321
|
-
const { parent } = child;
|
|
1322
|
-
if (parent === null || !isChildStore(child) || ((_a = child.transactionMeta) == null ? void 0 : _a.phase) !== `building`) {
|
|
1323
|
-
store.logger.warn(
|
|
1324
|
-
`\u{1F41E}`,
|
|
1325
|
-
`transaction`,
|
|
1326
|
-
`???`,
|
|
1327
|
-
`applyTransaction called outside of a transaction. This is probably a bug in AtomIO.`
|
|
1328
|
-
);
|
|
1329
|
-
return;
|
|
1330
|
-
}
|
|
1331
|
-
child.transactionMeta.phase = `applying`;
|
|
1332
|
-
child.transactionMeta.update.output = output;
|
|
1333
|
-
parent.child = null;
|
|
1334
|
-
parent.on.transactionApplying.next(child.transactionMeta);
|
|
1335
|
-
const { updates } = child.transactionMeta.update;
|
|
1336
|
-
store.logger.info(
|
|
1337
|
-
`\u{1F6C4}`,
|
|
1338
|
-
`transaction`,
|
|
1339
|
-
child.transactionMeta.update.key,
|
|
1340
|
-
`Applying transaction with ${updates.length} updates:`,
|
|
1341
|
-
updates
|
|
1342
|
-
);
|
|
1343
|
-
for (const tracker of child.trackers.values()) {
|
|
1344
|
-
const mutableKey = tracker.mutableState.key;
|
|
1345
|
-
if (!parent.atoms.has(mutableKey)) {
|
|
1346
|
-
const atom = child.atoms.get(mutableKey);
|
|
1347
|
-
atom == null ? void 0 : atom.install(parent);
|
|
1348
|
-
}
|
|
1349
|
-
tracker.dispose();
|
|
1350
|
-
}
|
|
1351
|
-
ingestTransactionUpdate(`newValue`, child.transactionMeta.update, parent);
|
|
1352
|
-
if (isRootStore(parent)) {
|
|
1353
|
-
setEpochNumberOfAction(
|
|
1354
|
-
child.transactionMeta.update.key,
|
|
1355
|
-
child.transactionMeta.update.epoch,
|
|
1356
|
-
parent
|
|
1357
|
-
);
|
|
1358
|
-
const myTransaction = withdraw(
|
|
1359
|
-
{ key: child.transactionMeta.update.key, type: `transaction` },
|
|
1360
|
-
store
|
|
1361
|
-
);
|
|
1362
|
-
myTransaction == null ? void 0 : myTransaction.subject.next(child.transactionMeta.update);
|
|
1363
|
-
store.logger.info(
|
|
1364
|
-
`\u{1F6EC}`,
|
|
1365
|
-
`transaction`,
|
|
1366
|
-
child.transactionMeta.update.key,
|
|
1367
|
-
`Finished applying transaction.`
|
|
1368
|
-
);
|
|
1369
|
-
} else if (isChildStore(parent)) {
|
|
1370
|
-
parent.transactionMeta.update.updates.push(child.transactionMeta.update);
|
|
1371
|
-
}
|
|
1372
|
-
parent.on.transactionApplying.next(null);
|
|
1373
|
-
};
|
|
1374
|
-
|
|
1375
|
-
// internal/src/transaction/assign-transaction-to-continuity.ts
|
|
1376
|
-
function assignTransactionToContinuity(continuityKey, transactionKey, store) {
|
|
1377
|
-
const isRoot = isRootStore(store);
|
|
1378
|
-
if (!isRoot) {
|
|
1379
|
-
return;
|
|
1380
|
-
}
|
|
1381
|
-
const { epoch, actionContinuities } = store.transactionMeta;
|
|
1382
|
-
actionContinuities.set(continuityKey, transactionKey);
|
|
1383
|
-
if (!epoch.has(continuityKey)) {
|
|
1384
|
-
epoch.set(continuityKey, -1);
|
|
1385
|
-
}
|
|
1386
|
-
}
|
|
1387
|
-
|
|
1388
|
-
// internal/src/lazy-map.ts
|
|
1389
|
-
var LazyMap = class extends Map {
|
|
1390
|
-
constructor(source) {
|
|
1391
|
-
super();
|
|
1392
|
-
this.source = source;
|
|
1393
|
-
this.deleted = /* @__PURE__ */ new Set();
|
|
1394
|
-
}
|
|
1395
|
-
get(key) {
|
|
1396
|
-
const has = super.has(key);
|
|
1397
|
-
if (has) {
|
|
1398
|
-
return super.get(key);
|
|
1399
|
-
}
|
|
1400
|
-
if (!this.deleted.has(key) && this.source.has(key)) {
|
|
1401
|
-
const value = this.source.get(key);
|
|
1402
|
-
return value;
|
|
1403
|
-
}
|
|
1404
|
-
return void 0;
|
|
1405
|
-
}
|
|
1406
|
-
set(key, value) {
|
|
1407
|
-
this.deleted.delete(key);
|
|
1408
|
-
return super.set(key, value);
|
|
1409
|
-
}
|
|
1410
|
-
hasOwn(key) {
|
|
1411
|
-
return super.has(key);
|
|
1412
|
-
}
|
|
1413
|
-
has(key) {
|
|
1414
|
-
return !this.deleted.has(key) && (super.has(key) || this.source.has(key));
|
|
1415
|
-
}
|
|
1416
|
-
delete(key) {
|
|
1417
|
-
this.deleted.add(key);
|
|
1418
|
-
return super.delete(key);
|
|
1419
|
-
}
|
|
1420
|
-
};
|
|
1421
|
-
|
|
1422
|
-
// internal/src/transaction/build-transaction.ts
|
|
1423
|
-
var buildTransaction = (key, params, store, id) => {
|
|
1424
|
-
const parent = newest(store);
|
|
1425
|
-
const childBase = {
|
|
1426
|
-
parent,
|
|
1427
|
-
child: null,
|
|
1428
|
-
on: parent.on,
|
|
1429
|
-
loggers: parent.loggers,
|
|
1430
|
-
logger: parent.logger,
|
|
1431
|
-
config: parent.config,
|
|
1432
|
-
atoms: new LazyMap(parent.atoms),
|
|
1433
|
-
atomsThatAreDefault: new Set(parent.atomsThatAreDefault),
|
|
1434
|
-
families: new LazyMap(parent.families),
|
|
1435
|
-
operation: { open: false },
|
|
1436
|
-
readonlySelectors: new LazyMap(parent.readonlySelectors),
|
|
1437
|
-
timelines: new LazyMap(parent.timelines),
|
|
1438
|
-
timelineAtoms: new Junction(parent.timelineAtoms.toJSON()),
|
|
1439
|
-
trackers: /* @__PURE__ */ new Map(),
|
|
1440
|
-
transactions: new LazyMap(parent.transactions),
|
|
1441
|
-
selectorAtoms: new Junction(parent.selectorAtoms.toJSON()),
|
|
1442
|
-
selectorGraph: new Junction(parent.selectorGraph.toJSON(), {
|
|
1443
|
-
makeContentKey: (...keys) => keys.sort().join(`:`)
|
|
1444
|
-
}),
|
|
1445
|
-
selectors: new LazyMap(parent.selectors),
|
|
1446
|
-
valueMap: new LazyMap(parent.valueMap),
|
|
1447
|
-
molecules: new LazyMap(parent.molecules),
|
|
1448
|
-
moleculeFamilies: new LazyMap(parent.moleculeFamilies),
|
|
1449
|
-
miscResources: new LazyMap(parent.miscResources)
|
|
1450
|
-
};
|
|
1451
|
-
const epoch = getEpochNumberOfAction(key, store);
|
|
1452
|
-
const transactionMeta = {
|
|
1453
|
-
phase: `building`,
|
|
1454
|
-
update: {
|
|
1455
|
-
type: `transaction_update`,
|
|
1456
|
-
key,
|
|
1457
|
-
id,
|
|
1458
|
-
epoch: epoch === void 0 ? Number.NaN : epoch + 1,
|
|
1459
|
-
updates: [],
|
|
1460
|
-
params,
|
|
1461
|
-
output: void 0
|
|
1462
|
-
},
|
|
1463
|
-
transactors: {
|
|
1464
|
-
get: (token) => getFromStore(token, child),
|
|
1465
|
-
set: (token, value) => {
|
|
1466
|
-
setIntoStore(token, value, child);
|
|
1467
|
-
},
|
|
1468
|
-
run: (token, identifier = arbitrary()) => actUponStore(token, identifier, child),
|
|
1469
|
-
find: (token, k) => findInStore(token, k, child),
|
|
1470
|
-
seek: (token, k) => seekInStore(token, k, child),
|
|
1471
|
-
json: (token) => getJsonToken(token, child),
|
|
1472
|
-
make: (context, family, k, ...args) => makeMoleculeInStore(child, context, family, k, ...args),
|
|
1473
|
-
dispose: (token) => {
|
|
1474
|
-
disposeFromStore(token, child);
|
|
1475
|
-
},
|
|
1476
|
-
env: () => getEnvironmentData(child)
|
|
1477
|
-
}
|
|
1478
|
-
};
|
|
1479
|
-
const child = Object.assign(childBase, {
|
|
1480
|
-
transactionMeta
|
|
1481
|
-
});
|
|
1482
|
-
parent.child = child;
|
|
1483
|
-
store.logger.info(
|
|
1484
|
-
`\u{1F6EB}`,
|
|
1485
|
-
`transaction`,
|
|
1486
|
-
key,
|
|
1487
|
-
`Building transaction with params:`,
|
|
1488
|
-
params
|
|
1489
|
-
);
|
|
1490
|
-
return child;
|
|
1491
|
-
};
|
|
1492
|
-
|
|
1493
|
-
// internal/src/transaction/create-transaction.ts
|
|
1494
|
-
function createTransaction(options, store) {
|
|
1495
|
-
const newTransaction = {
|
|
1496
|
-
key: options.key,
|
|
1497
|
-
type: `transaction`,
|
|
1498
|
-
run: (params, id) => {
|
|
1499
|
-
const childStore = buildTransaction(options.key, params, store, id);
|
|
1500
|
-
try {
|
|
1501
|
-
const target2 = newest(store);
|
|
1502
|
-
const { transactors } = childStore.transactionMeta;
|
|
1503
|
-
const output = options.do(transactors, ...params);
|
|
1504
|
-
applyTransaction(output, target2);
|
|
1505
|
-
return output;
|
|
1506
|
-
} catch (thrown) {
|
|
1507
|
-
abortTransaction(target);
|
|
1508
|
-
store.logger.warn(`\u{1F4A5}`, `transaction`, options.key, `caught:`, thrown);
|
|
1509
|
-
throw thrown;
|
|
1510
|
-
}
|
|
1511
|
-
},
|
|
1512
|
-
install: (s) => createTransaction(options, s),
|
|
1513
|
-
subject: new Subject()
|
|
1514
|
-
};
|
|
1515
|
-
const target = newest(store);
|
|
1516
|
-
target.transactions.set(newTransaction.key, newTransaction);
|
|
1517
|
-
const token = deposit(newTransaction);
|
|
1518
|
-
store.on.transactionCreation.next(token);
|
|
1519
|
-
return token;
|
|
1520
|
-
}
|
|
1521
|
-
|
|
1522
|
-
// internal/src/transaction/get-epoch-number.ts
|
|
1523
|
-
function getContinuityKey(transactionKey, store) {
|
|
1524
|
-
const isRoot = isRootStore(store);
|
|
1525
|
-
const continuity = isRoot ? store.transactionMeta.actionContinuities.getRelatedKey(transactionKey) : void 0;
|
|
1526
|
-
return continuity;
|
|
1527
|
-
}
|
|
1528
|
-
function getEpochNumberOfContinuity(continuityKey, store) {
|
|
1529
|
-
const isRoot = isRootStore(store);
|
|
1530
|
-
const epoch = isRoot && continuityKey ? store.transactionMeta.epoch.get(continuityKey) : void 0;
|
|
1531
|
-
return epoch;
|
|
1532
|
-
}
|
|
1533
|
-
function getEpochNumberOfAction(transactionKey, store) {
|
|
1534
|
-
const isRoot = isRootStore(store);
|
|
1535
|
-
const continuity = isRoot ? store.transactionMeta.actionContinuities.getRelatedKey(transactionKey) : void 0;
|
|
1536
|
-
const epoch = isRoot && continuity !== void 0 ? store.transactionMeta.epoch.get(continuity) : void 0;
|
|
1537
|
-
return epoch;
|
|
1538
|
-
}
|
|
1539
|
-
|
|
1540
|
-
// internal/src/transaction/index.ts
|
|
1541
|
-
var TRANSACTION_PHASES = [`idle`, `building`, `applying`];
|
|
1542
|
-
|
|
1543
|
-
// internal/src/molecule/dispose-molecule.ts
|
|
1544
|
-
function disposeMolecule(token, store) {
|
|
1545
|
-
var _a;
|
|
1546
|
-
let molecule;
|
|
1547
|
-
try {
|
|
1548
|
-
molecule = withdraw(token, store);
|
|
1549
|
-
} catch (thrown) {
|
|
1550
|
-
if (thrown instanceof Error) {
|
|
1551
|
-
store.logger.error(
|
|
1552
|
-
`\u{1F41E}`,
|
|
1553
|
-
`molecule`,
|
|
1554
|
-
JSON.stringify(token.key),
|
|
1555
|
-
`Failed to dispose molecule, because it was not found in the store.`,
|
|
1556
|
-
thrown.message
|
|
1557
|
-
);
|
|
1558
|
-
}
|
|
1559
|
-
return;
|
|
1560
|
-
}
|
|
1561
|
-
const { family } = token;
|
|
1562
|
-
for (const state of molecule.tokens.values()) {
|
|
1563
|
-
disposeFromStore(state, store);
|
|
1564
|
-
}
|
|
1565
|
-
for (const child of molecule.below.values()) {
|
|
1566
|
-
if (((_a = child.family) == null ? void 0 : _a.dependsOn) === `all`) {
|
|
1567
|
-
disposeMolecule(child, store);
|
|
1568
|
-
} else {
|
|
1569
|
-
child.above.delete(molecule.stringKey);
|
|
1570
|
-
if (child.above.size === 0) {
|
|
1571
|
-
disposeMolecule(child, store);
|
|
1572
|
-
}
|
|
1573
|
-
}
|
|
1154
|
+
const values = [];
|
|
1155
|
+
for (const stateToken of molecule.tokens.values()) {
|
|
1156
|
+
const tokenFamily = stateToken.family;
|
|
1157
|
+
values.push([tokenFamily.key, store.valueMap.get(stateToken.key)]);
|
|
1574
1158
|
}
|
|
1575
|
-
molecule.below.clear();
|
|
1576
1159
|
if (family) {
|
|
1577
1160
|
const Formula = withdraw(family, store);
|
|
1578
1161
|
const disposalEvent = {
|
|
1579
1162
|
type: `molecule_disposal`,
|
|
1580
1163
|
token,
|
|
1581
1164
|
family,
|
|
1582
|
-
context
|
|
1583
|
-
|
|
1584
|
-
var _a2;
|
|
1585
|
-
return (_a2 = t.family) == null ? void 0 : _a2.key;
|
|
1586
|
-
}).filter((k) => typeof k === `string`)
|
|
1165
|
+
context,
|
|
1166
|
+
values
|
|
1587
1167
|
};
|
|
1588
1168
|
if (token.family) {
|
|
1589
1169
|
disposalEvent.family = token.family;
|
|
1590
1170
|
}
|
|
1171
|
+
for (const state of molecule.tokens.values()) {
|
|
1172
|
+
disposeFromStore(state, store);
|
|
1173
|
+
}
|
|
1174
|
+
for (const child of molecule.below.values()) {
|
|
1175
|
+
if (((_a = child.family) == null ? void 0 : _a.dependsOn) === `all`) {
|
|
1176
|
+
disposeMolecule(child, store);
|
|
1177
|
+
} else {
|
|
1178
|
+
child.above.delete(molecule.stringKey);
|
|
1179
|
+
if (child.above.size === 0) {
|
|
1180
|
+
disposeMolecule(child, store);
|
|
1181
|
+
}
|
|
1182
|
+
}
|
|
1183
|
+
}
|
|
1184
|
+
molecule.below.clear();
|
|
1591
1185
|
const isTransaction = isChildStore(store) && store.transactionMeta.phase === `building`;
|
|
1592
1186
|
if (isTransaction) {
|
|
1593
1187
|
store.transactionMeta.update.updates.push(disposalEvent);
|
|
@@ -1630,13 +1224,8 @@ function initFamilyMemberInStore(token, key, store) {
|
|
|
1630
1224
|
}
|
|
1631
1225
|
const state = family(key);
|
|
1632
1226
|
const target = newest(store);
|
|
1633
|
-
if (state.family) {
|
|
1634
|
-
if (
|
|
1635
|
-
target.transactionMeta.update.updates.push({
|
|
1636
|
-
type: `state_creation`,
|
|
1637
|
-
token: state
|
|
1638
|
-
});
|
|
1639
|
-
} else {
|
|
1227
|
+
if (state.family && target.moleculeInProgress === null) {
|
|
1228
|
+
if (isRootStore(target)) {
|
|
1640
1229
|
switch (state.type) {
|
|
1641
1230
|
case `atom`:
|
|
1642
1231
|
case `mutable_atom`:
|
|
@@ -1647,9 +1236,14 @@ function initFamilyMemberInStore(token, key, store) {
|
|
|
1647
1236
|
store.on.selectorCreation.next(state);
|
|
1648
1237
|
break;
|
|
1649
1238
|
}
|
|
1650
|
-
}
|
|
1651
|
-
|
|
1652
|
-
|
|
1239
|
+
} else if (isChildStore(target) && target.on.transactionApplying.state === null) {
|
|
1240
|
+
target.transactionMeta.update.updates.push({
|
|
1241
|
+
type: `state_creation`,
|
|
1242
|
+
token: state
|
|
1243
|
+
});
|
|
1244
|
+
}
|
|
1245
|
+
}
|
|
1246
|
+
return state;
|
|
1653
1247
|
}
|
|
1654
1248
|
function seekInStore(token, key, store) {
|
|
1655
1249
|
const subKey = json.stringifyJson(key);
|
|
@@ -1694,291 +1288,715 @@ function findInStore(token, key, store) {
|
|
|
1694
1288
|
return state;
|
|
1695
1289
|
}
|
|
1696
1290
|
|
|
1697
|
-
// internal/src/
|
|
1698
|
-
|
|
1699
|
-
var
|
|
1700
|
-
|
|
1701
|
-
|
|
1291
|
+
// internal/src/molecule/create-molecule-family.ts
|
|
1292
|
+
function createMoleculeFamily(options, store) {
|
|
1293
|
+
var _a;
|
|
1294
|
+
const subject = new Subject();
|
|
1295
|
+
const token = {
|
|
1296
|
+
type: `molecule_family`,
|
|
1297
|
+
key: options.key,
|
|
1298
|
+
dependsOn: (_a = options.dependsOn) != null ? _a : `all`
|
|
1299
|
+
};
|
|
1300
|
+
const family = __spreadProps(__spreadValues({}, token), {
|
|
1301
|
+
subject,
|
|
1302
|
+
new: options.new
|
|
1303
|
+
});
|
|
1304
|
+
store.moleculeFamilies.set(options.key, family);
|
|
1305
|
+
return token;
|
|
1306
|
+
}
|
|
1702
1307
|
|
|
1703
|
-
// internal/src/
|
|
1704
|
-
|
|
1705
|
-
const
|
|
1706
|
-
|
|
1707
|
-
|
|
1308
|
+
// internal/src/molecule/grow-molecule-in-store.ts
|
|
1309
|
+
function growMoleculeInStore(molecule, family, store) {
|
|
1310
|
+
const stateToken = initFamilyMemberInStore(family, molecule.key, store);
|
|
1311
|
+
molecule.tokens.set(stateToken.key, stateToken);
|
|
1312
|
+
const isTransaction = isChildStore(store) && store.transactionMeta.phase === `building`;
|
|
1313
|
+
const moleculeInProgress = store.moleculeInProgress === molecule.key;
|
|
1314
|
+
if (!isTransaction && !moleculeInProgress) {
|
|
1315
|
+
molecule.subject.next({ type: `state_creation`, token: stateToken });
|
|
1316
|
+
}
|
|
1317
|
+
return stateToken;
|
|
1318
|
+
}
|
|
1708
1319
|
|
|
1709
|
-
// internal/src/
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
const indirectDependencyKeys = getSelectorDependencyKeys(
|
|
1713
|
-
directDependencyKey,
|
|
1320
|
+
// internal/src/get-environment-data.ts
|
|
1321
|
+
function getEnvironmentData(store) {
|
|
1322
|
+
return {
|
|
1714
1323
|
store
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
|
|
1721
|
-
|
|
1722
|
-
|
|
1723
|
-
|
|
1324
|
+
};
|
|
1325
|
+
}
|
|
1326
|
+
|
|
1327
|
+
// internal/src/get-state/get-from-store.ts
|
|
1328
|
+
function getFromStore(token, store) {
|
|
1329
|
+
if (token.type === `molecule`) {
|
|
1330
|
+
try {
|
|
1331
|
+
const molecule = withdraw(token, store);
|
|
1332
|
+
return molecule.instance;
|
|
1333
|
+
} catch (_) {
|
|
1334
|
+
return void 0;
|
|
1724
1335
|
}
|
|
1725
|
-
|
|
1726
|
-
|
|
1727
|
-
|
|
1728
|
-
|
|
1729
|
-
|
|
1730
|
-
|
|
1336
|
+
}
|
|
1337
|
+
const state = withdraw(token, store);
|
|
1338
|
+
return readOrComputeValue(state, store);
|
|
1339
|
+
}
|
|
1340
|
+
var Molecule = class {
|
|
1341
|
+
constructor(ctx, key, family) {
|
|
1342
|
+
this.key = key;
|
|
1343
|
+
this.type = `molecule`;
|
|
1344
|
+
this.subject = new Subject();
|
|
1345
|
+
this.tokens = /* @__PURE__ */ new Map();
|
|
1346
|
+
this.above = /* @__PURE__ */ new Map();
|
|
1347
|
+
this.below = /* @__PURE__ */ new Map();
|
|
1348
|
+
this.joins = /* @__PURE__ */ new Map();
|
|
1349
|
+
this.stringKey = json.stringifyJson(key);
|
|
1350
|
+
if (family) {
|
|
1351
|
+
this.family = family;
|
|
1352
|
+
}
|
|
1353
|
+
if (ctx) {
|
|
1354
|
+
if (Array.isArray(ctx)) {
|
|
1355
|
+
for (const molecule of ctx) {
|
|
1356
|
+
this.above.set(molecule.stringKey, molecule);
|
|
1357
|
+
}
|
|
1358
|
+
} else {
|
|
1359
|
+
this.above.set(ctx.stringKey, ctx);
|
|
1360
|
+
}
|
|
1731
1361
|
}
|
|
1732
1362
|
}
|
|
1733
|
-
return rootKeys;
|
|
1734
|
-
};
|
|
1735
|
-
var traceAllSelectorAtoms = (selector, store) => {
|
|
1736
|
-
const selectorKey = selector.key;
|
|
1737
|
-
const directDependencyKeys = getSelectorDependencyKeys(selectorKey, store);
|
|
1738
|
-
return directDependencyKeys.flatMap(
|
|
1739
|
-
(depKey) => isAtomKey(depKey, store) ? depKey : traceSelectorAtoms(selectorKey, depKey, store)
|
|
1740
|
-
);
|
|
1741
1363
|
};
|
|
1742
1364
|
|
|
1743
|
-
// internal/src/
|
|
1744
|
-
|
|
1365
|
+
// internal/src/molecule/make-molecule-in-store.ts
|
|
1366
|
+
function makeMoleculeInStore(store, context, familyToken, key, ...params) {
|
|
1745
1367
|
const target = newest(store);
|
|
1746
|
-
|
|
1747
|
-
|
|
1748
|
-
|
|
1749
|
-
|
|
1750
|
-
|
|
1751
|
-
|
|
1752
|
-
|
|
1753
|
-
|
|
1754
|
-
|
|
1755
|
-
|
|
1756
|
-
|
|
1757
|
-
|
|
1758
|
-
const rootKeys = traceSelectorAtoms(selectorKey, dependency.key, store);
|
|
1759
|
-
store.logger.info(
|
|
1760
|
-
`\u{1F50D}`,
|
|
1761
|
-
`selector`,
|
|
1762
|
-
selectorKey,
|
|
1763
|
-
`discovers root atoms: [ ${rootKeys.map((key) => `"${key}"`).join(`, `)} ]`
|
|
1764
|
-
);
|
|
1765
|
-
for (const atomKey of rootKeys) {
|
|
1766
|
-
target.selectorAtoms = target.selectorAtoms.set({
|
|
1767
|
-
selectorKey,
|
|
1768
|
-
atomKey
|
|
1769
|
-
});
|
|
1368
|
+
target.moleculeInProgress = key;
|
|
1369
|
+
const contextArray = Array.isArray(context) ? context : [context];
|
|
1370
|
+
const owners = contextArray.map((ctx) => {
|
|
1371
|
+
if (ctx instanceof Molecule) {
|
|
1372
|
+
return ctx;
|
|
1373
|
+
}
|
|
1374
|
+
const stringKey = json.stringifyJson(ctx.key);
|
|
1375
|
+
const molecule2 = store.molecules.get(stringKey);
|
|
1376
|
+
if (!molecule2) {
|
|
1377
|
+
throw new Error(
|
|
1378
|
+
`Molecule ${stringKey} not found in store "${store.config.name}"`
|
|
1379
|
+
);
|
|
1770
1380
|
}
|
|
1381
|
+
return molecule2;
|
|
1382
|
+
});
|
|
1383
|
+
const molecule = new Molecule(owners, key, familyToken);
|
|
1384
|
+
target.molecules.set(json.stringifyJson(key), molecule);
|
|
1385
|
+
for (const owner of owners) {
|
|
1386
|
+
owner.below.set(molecule.stringKey, molecule);
|
|
1771
1387
|
}
|
|
1772
|
-
|
|
1773
|
-
|
|
1774
|
-
|
|
1775
|
-
|
|
1776
|
-
|
|
1777
|
-
|
|
1778
|
-
|
|
1779
|
-
|
|
1780
|
-
store
|
|
1781
|
-
|
|
1782
|
-
|
|
1783
|
-
|
|
1784
|
-
|
|
1785
|
-
|
|
1786
|
-
|
|
1787
|
-
|
|
1788
|
-
|
|
1789
|
-
|
|
1790
|
-
|
|
1791
|
-
|
|
1792
|
-
|
|
1793
|
-
{
|
|
1794
|
-
|
|
1388
|
+
const transactors = {
|
|
1389
|
+
get: (t) => getFromStore(t, newest(store)),
|
|
1390
|
+
set: (t, newValue) => {
|
|
1391
|
+
setIntoStore(t, newValue, newest(store));
|
|
1392
|
+
},
|
|
1393
|
+
seek: (t, k) => seekInStore(t, k, newest(store)),
|
|
1394
|
+
json: (t) => getJsonToken(t, newest(store)),
|
|
1395
|
+
run: (t, i = arbitrary()) => actUponStore(t, i, newest(store)),
|
|
1396
|
+
make: (ctx, f, k, ...args) => makeMoleculeInStore(newest(store), ctx, f, k, ...args),
|
|
1397
|
+
dispose: (t) => {
|
|
1398
|
+
disposeFromStore(t, newest(store));
|
|
1399
|
+
},
|
|
1400
|
+
env: () => getEnvironmentData(newest(store)),
|
|
1401
|
+
bond: (f) => growMoleculeInStore(
|
|
1402
|
+
molecule,
|
|
1403
|
+
withdraw(f, store),
|
|
1404
|
+
newest(store)
|
|
1405
|
+
),
|
|
1406
|
+
claim: (below, options) => {
|
|
1407
|
+
const { exclusive } = options;
|
|
1408
|
+
const belowMolecule = newest(store).molecules.get(json.stringifyJson(below.key));
|
|
1409
|
+
if (belowMolecule) {
|
|
1410
|
+
if (exclusive) {
|
|
1411
|
+
for (const value of belowMolecule.above.values()) {
|
|
1412
|
+
value.below.delete(belowMolecule.stringKey);
|
|
1413
|
+
}
|
|
1414
|
+
belowMolecule.above.clear();
|
|
1415
|
+
belowMolecule.above.set(molecule.stringKey, molecule);
|
|
1416
|
+
molecule.below.set(belowMolecule.stringKey, belowMolecule);
|
|
1417
|
+
} else {
|
|
1418
|
+
belowMolecule.above.set(molecule.stringKey, molecule);
|
|
1419
|
+
molecule.below.set(belowMolecule.stringKey, belowMolecule);
|
|
1420
|
+
}
|
|
1795
1421
|
}
|
|
1796
|
-
|
|
1797
|
-
|
|
1798
|
-
|
|
1799
|
-
|
|
1800
|
-
|
|
1801
|
-
|
|
1802
|
-
|
|
1803
|
-
|
|
1804
|
-
|
|
1805
|
-
|
|
1806
|
-
|
|
1807
|
-
|
|
1808
|
-
|
|
1809
|
-
|
|
1810
|
-
var createReadonlySelector = (options, family, store) => {
|
|
1811
|
-
const target = newest(store);
|
|
1812
|
-
const subject = new Subject();
|
|
1813
|
-
const { get, find, seek, json } = registerSelector(options.key, target);
|
|
1814
|
-
const getSelf = () => {
|
|
1815
|
-
const value = options.get({ get, find, seek, json });
|
|
1816
|
-
cacheValue(options.key, value, subject, newest(store));
|
|
1817
|
-
return value;
|
|
1422
|
+
},
|
|
1423
|
+
join: (joinToken) => {
|
|
1424
|
+
const join = data.getJoin(joinToken, store);
|
|
1425
|
+
join.molecules.set(json.stringifyJson(key), molecule);
|
|
1426
|
+
molecule.joins.set(joinToken.key, join);
|
|
1427
|
+
return joinToken;
|
|
1428
|
+
},
|
|
1429
|
+
spawn: (f, k, ...p) => makeMoleculeInStore(
|
|
1430
|
+
newest(store),
|
|
1431
|
+
[molecule],
|
|
1432
|
+
withdraw(f, store),
|
|
1433
|
+
k,
|
|
1434
|
+
...p
|
|
1435
|
+
)
|
|
1818
1436
|
};
|
|
1819
|
-
const
|
|
1820
|
-
|
|
1821
|
-
|
|
1822
|
-
get: getSelf,
|
|
1823
|
-
type: `readonly_selector`
|
|
1824
|
-
}), family && { family });
|
|
1825
|
-
target.readonlySelectors.set(options.key, readonlySelector);
|
|
1826
|
-
const initialValue = getSelf();
|
|
1827
|
-
store.logger.info(
|
|
1828
|
-
`\u2728`,
|
|
1829
|
-
readonlySelector.type,
|
|
1830
|
-
readonlySelector.key,
|
|
1831
|
-
`=`,
|
|
1832
|
-
initialValue
|
|
1833
|
-
);
|
|
1437
|
+
const family = withdraw(familyToken, store);
|
|
1438
|
+
const Constructor = family.new;
|
|
1439
|
+
molecule.instance = new Constructor(transactors, key, ...params);
|
|
1834
1440
|
const token = {
|
|
1835
|
-
|
|
1836
|
-
|
|
1441
|
+
type: `molecule`,
|
|
1442
|
+
key,
|
|
1443
|
+
family: familyToken
|
|
1837
1444
|
};
|
|
1838
|
-
|
|
1839
|
-
|
|
1445
|
+
const update = {
|
|
1446
|
+
type: `molecule_creation`,
|
|
1447
|
+
token,
|
|
1448
|
+
family: familyToken,
|
|
1449
|
+
context: contextArray,
|
|
1450
|
+
params
|
|
1451
|
+
};
|
|
1452
|
+
if (isRootStore(target)) {
|
|
1453
|
+
family.subject.next(update);
|
|
1454
|
+
} else if (isChildStore(target) && target.on.transactionApplying.state === null) {
|
|
1455
|
+
target.transactionMeta.update.updates.push(update);
|
|
1840
1456
|
}
|
|
1457
|
+
target.moleculeInProgress = null;
|
|
1841
1458
|
return token;
|
|
1842
|
-
}
|
|
1459
|
+
}
|
|
1843
1460
|
|
|
1844
|
-
// internal/src/
|
|
1845
|
-
|
|
1846
|
-
|
|
1847
|
-
|
|
1848
|
-
|
|
1849
|
-
|
|
1850
|
-
|
|
1851
|
-
|
|
1852
|
-
|
|
1853
|
-
|
|
1854
|
-
return value;
|
|
1855
|
-
};
|
|
1856
|
-
const setSelf = (next) => {
|
|
1857
|
-
const oldValue = getSelf();
|
|
1858
|
-
const newValue = become(next)(oldValue);
|
|
1859
|
-
store.logger.info(
|
|
1860
|
-
`\u{1F4DD}`,
|
|
1861
|
-
`selector`,
|
|
1862
|
-
options.key,
|
|
1863
|
-
`set (`,
|
|
1864
|
-
oldValue,
|
|
1865
|
-
`->`,
|
|
1866
|
-
newValue,
|
|
1867
|
-
`)`
|
|
1868
|
-
);
|
|
1869
|
-
cacheValue(options.key, newValue, subject, store);
|
|
1870
|
-
markDone(options.key, store);
|
|
1871
|
-
if (isRootStore(target)) {
|
|
1872
|
-
subject.next({ newValue, oldValue });
|
|
1461
|
+
// internal/src/ingest-updates/ingest-creation-disposal.ts
|
|
1462
|
+
function ingestCreationEvent(update, applying, store) {
|
|
1463
|
+
switch (applying) {
|
|
1464
|
+
case `newValue`: {
|
|
1465
|
+
createInStore(update.token, store);
|
|
1466
|
+
break;
|
|
1467
|
+
}
|
|
1468
|
+
case `oldValue`: {
|
|
1469
|
+
disposeFromStore(update.token, store);
|
|
1470
|
+
break;
|
|
1873
1471
|
}
|
|
1874
|
-
options.set(transactors, newValue);
|
|
1875
|
-
};
|
|
1876
|
-
const mySelector = __spreadValues(__spreadProps(__spreadValues({}, options), {
|
|
1877
|
-
subject,
|
|
1878
|
-
install: (s) => createWritableSelector(options, family, s),
|
|
1879
|
-
get: getSelf,
|
|
1880
|
-
set: setSelf,
|
|
1881
|
-
type: `selector`
|
|
1882
|
-
}), family && { family });
|
|
1883
|
-
target.selectors.set(options.key, mySelector);
|
|
1884
|
-
const initialValue = getSelf();
|
|
1885
|
-
store.logger.info(`\u2728`, mySelector.type, mySelector.key, `=`, initialValue);
|
|
1886
|
-
const token = {
|
|
1887
|
-
key: options.key,
|
|
1888
|
-
type: `selector`
|
|
1889
|
-
};
|
|
1890
|
-
if (family) {
|
|
1891
|
-
token.family = family;
|
|
1892
1472
|
}
|
|
1893
|
-
|
|
1894
|
-
|
|
1473
|
+
}
|
|
1474
|
+
function ingestDisposalEvent(update, applying, store) {
|
|
1475
|
+
switch (applying) {
|
|
1476
|
+
case `newValue`: {
|
|
1477
|
+
disposeFromStore(update.token, store);
|
|
1478
|
+
break;
|
|
1479
|
+
}
|
|
1480
|
+
case `oldValue`: {
|
|
1481
|
+
createInStore(update.token, store);
|
|
1482
|
+
store.valueMap.set(update.token.key, update.value);
|
|
1483
|
+
break;
|
|
1484
|
+
}
|
|
1485
|
+
}
|
|
1486
|
+
}
|
|
1487
|
+
function createInStore(token, store) {
|
|
1488
|
+
if (token.family) {
|
|
1489
|
+
const family = store.families.get(token.family.key);
|
|
1490
|
+
if (family) {
|
|
1491
|
+
const molecule = store.molecules.get(token.family.subKey);
|
|
1492
|
+
if (molecule) {
|
|
1493
|
+
growMoleculeInStore(molecule, family, store);
|
|
1494
|
+
return;
|
|
1495
|
+
}
|
|
1496
|
+
if (store.config.lifespan === `immortal`) {
|
|
1497
|
+
throw new Error(`No molecule found for key "${token.family.subKey}"`);
|
|
1498
|
+
}
|
|
1499
|
+
initFamilyMemberInStore(family, json.parseJson(token.family.subKey), store);
|
|
1500
|
+
}
|
|
1501
|
+
}
|
|
1502
|
+
}
|
|
1503
|
+
function ingestMoleculeCreationEvent(update, applying, store) {
|
|
1504
|
+
switch (applying) {
|
|
1505
|
+
case `newValue`:
|
|
1506
|
+
makeMoleculeInStore(
|
|
1507
|
+
store,
|
|
1508
|
+
update.context,
|
|
1509
|
+
update.family,
|
|
1510
|
+
update.token.key,
|
|
1511
|
+
...update.params
|
|
1512
|
+
);
|
|
1513
|
+
break;
|
|
1514
|
+
case `oldValue`:
|
|
1515
|
+
disposeFromStore(update.token, store);
|
|
1516
|
+
break;
|
|
1517
|
+
}
|
|
1518
|
+
}
|
|
1519
|
+
function ingestMoleculeDisposalEvent(update, applying, store) {
|
|
1520
|
+
switch (applying) {
|
|
1521
|
+
case `newValue`:
|
|
1522
|
+
disposeFromStore(update.token, store);
|
|
1523
|
+
break;
|
|
1524
|
+
case `oldValue`:
|
|
1525
|
+
{
|
|
1526
|
+
const moleculeToken = makeMoleculeInStore(
|
|
1527
|
+
store,
|
|
1528
|
+
update.context,
|
|
1529
|
+
update.family,
|
|
1530
|
+
update.token.key
|
|
1531
|
+
);
|
|
1532
|
+
for (const [familyKey, value] of update.values) {
|
|
1533
|
+
const memberKey = `${familyKey}(${json.stringifyJson(moleculeToken.key)})`;
|
|
1534
|
+
const molecule = withdraw(moleculeToken, store);
|
|
1535
|
+
const alreadyCreated = molecule.tokens.has(memberKey);
|
|
1536
|
+
const family = store.families.get(familyKey);
|
|
1537
|
+
if (family && !alreadyCreated) {
|
|
1538
|
+
growMoleculeInStore(molecule, family, store);
|
|
1539
|
+
}
|
|
1540
|
+
store.valueMap.set(memberKey, value);
|
|
1541
|
+
}
|
|
1542
|
+
}
|
|
1543
|
+
break;
|
|
1544
|
+
}
|
|
1545
|
+
}
|
|
1895
1546
|
|
|
1896
|
-
// internal/src/
|
|
1897
|
-
function
|
|
1898
|
-
const
|
|
1899
|
-
|
|
1900
|
-
|
|
1901
|
-
store.on.selectorCreation.next(state2);
|
|
1902
|
-
return state2;
|
|
1547
|
+
// internal/src/ingest-updates/ingest-selector-update.ts
|
|
1548
|
+
function ingestSelectorUpdate(applying, selectorUpdate, store) {
|
|
1549
|
+
const updates = applying === `newValue` ? selectorUpdate.atomUpdates : [...selectorUpdate.atomUpdates].reverse();
|
|
1550
|
+
for (const atomUpdate of updates) {
|
|
1551
|
+
ingestAtomUpdate(applying, atomUpdate, store);
|
|
1903
1552
|
}
|
|
1904
|
-
const state = createReadonlySelector(options, void 0, store);
|
|
1905
|
-
store.on.selectorCreation.next(state);
|
|
1906
|
-
return state;
|
|
1907
1553
|
}
|
|
1908
1554
|
|
|
1909
|
-
// internal/src/
|
|
1910
|
-
function
|
|
1555
|
+
// internal/src/ingest-updates/ingest-transaction-update.ts
|
|
1556
|
+
function ingestTransactionUpdate(applying, transactionUpdate, store) {
|
|
1557
|
+
const updates = applying === `newValue` ? transactionUpdate.updates : [...transactionUpdate.updates].reverse();
|
|
1558
|
+
for (const updateFromTransaction of updates) {
|
|
1559
|
+
switch (updateFromTransaction.type) {
|
|
1560
|
+
case `atom_update`:
|
|
1561
|
+
case `selector_update`:
|
|
1562
|
+
ingestAtomUpdate(applying, updateFromTransaction, store);
|
|
1563
|
+
break;
|
|
1564
|
+
case `state_creation`:
|
|
1565
|
+
ingestCreationEvent(updateFromTransaction, applying, store);
|
|
1566
|
+
break;
|
|
1567
|
+
case `state_disposal`:
|
|
1568
|
+
ingestDisposalEvent(updateFromTransaction, applying, store);
|
|
1569
|
+
break;
|
|
1570
|
+
case `molecule_creation`:
|
|
1571
|
+
ingestMoleculeCreationEvent(updateFromTransaction, applying, store);
|
|
1572
|
+
break;
|
|
1573
|
+
case `molecule_disposal`:
|
|
1574
|
+
ingestMoleculeDisposalEvent(updateFromTransaction, applying, store);
|
|
1575
|
+
break;
|
|
1576
|
+
case `transaction_update`:
|
|
1577
|
+
ingestTransactionUpdate(applying, updateFromTransaction, store);
|
|
1578
|
+
break;
|
|
1579
|
+
}
|
|
1580
|
+
}
|
|
1581
|
+
}
|
|
1582
|
+
|
|
1583
|
+
// internal/src/transaction/set-epoch-number.ts
|
|
1584
|
+
function setEpochNumberOfContinuity(continuityKey, newEpoch, store) {
|
|
1585
|
+
const isRoot = isRootStore(store);
|
|
1586
|
+
if (isRoot && continuityKey) {
|
|
1587
|
+
store.transactionMeta.epoch.set(continuityKey, newEpoch);
|
|
1588
|
+
}
|
|
1589
|
+
}
|
|
1590
|
+
function setEpochNumberOfAction(transactionKey, newEpoch, store) {
|
|
1591
|
+
const isRoot = isRootStore(store);
|
|
1592
|
+
if (!isRoot) {
|
|
1593
|
+
return;
|
|
1594
|
+
}
|
|
1595
|
+
const continuityKey = store.transactionMeta.actionContinuities.getRelatedKey(transactionKey);
|
|
1596
|
+
if (continuityKey !== void 0) {
|
|
1597
|
+
store.transactionMeta.epoch.set(continuityKey, newEpoch);
|
|
1598
|
+
}
|
|
1599
|
+
}
|
|
1600
|
+
|
|
1601
|
+
// internal/src/transaction/apply-transaction.ts
|
|
1602
|
+
var applyTransaction = (output, store) => {
|
|
1911
1603
|
var _a;
|
|
1912
|
-
const
|
|
1913
|
-
const {
|
|
1914
|
-
|
|
1915
|
-
|
|
1916
|
-
|
|
1917
|
-
|
|
1918
|
-
|
|
1919
|
-
|
|
1920
|
-
`Tried to dispose selector, but it does not exist in the store.`
|
|
1604
|
+
const child = newest(store);
|
|
1605
|
+
const { parent } = child;
|
|
1606
|
+
if (parent === null || !isChildStore(child) || ((_a = child.transactionMeta) == null ? void 0 : _a.phase) !== `building`) {
|
|
1607
|
+
store.logger.warn(
|
|
1608
|
+
`\u{1F41E}`,
|
|
1609
|
+
`transaction`,
|
|
1610
|
+
`???`,
|
|
1611
|
+
`applyTransaction called outside of a transaction. This is probably a bug in AtomIO.`
|
|
1921
1612
|
);
|
|
1922
|
-
|
|
1923
|
-
|
|
1924
|
-
|
|
1925
|
-
|
|
1926
|
-
|
|
1927
|
-
|
|
1613
|
+
return;
|
|
1614
|
+
}
|
|
1615
|
+
child.transactionMeta.phase = `applying`;
|
|
1616
|
+
child.transactionMeta.update.output = output;
|
|
1617
|
+
parent.child = null;
|
|
1618
|
+
parent.on.transactionApplying.next(child.transactionMeta);
|
|
1619
|
+
const { updates } = child.transactionMeta.update;
|
|
1620
|
+
store.logger.info(
|
|
1621
|
+
`\u{1F6C4}`,
|
|
1622
|
+
`transaction`,
|
|
1623
|
+
child.transactionMeta.update.key,
|
|
1624
|
+
`Applying transaction with ${updates.length} updates:`,
|
|
1625
|
+
updates
|
|
1626
|
+
);
|
|
1627
|
+
ingestTransactionUpdate(`newValue`, child.transactionMeta.update, parent);
|
|
1628
|
+
if (isRootStore(parent)) {
|
|
1629
|
+
setEpochNumberOfAction(
|
|
1630
|
+
child.transactionMeta.update.key,
|
|
1631
|
+
child.transactionMeta.update.epoch,
|
|
1632
|
+
parent
|
|
1928
1633
|
);
|
|
1929
|
-
|
|
1930
|
-
|
|
1931
|
-
|
|
1932
|
-
|
|
1933
|
-
|
|
1934
|
-
|
|
1935
|
-
|
|
1936
|
-
|
|
1937
|
-
|
|
1938
|
-
|
|
1939
|
-
|
|
1940
|
-
|
|
1941
|
-
|
|
1634
|
+
const myTransaction = withdraw(
|
|
1635
|
+
{ key: child.transactionMeta.update.key, type: `transaction` },
|
|
1636
|
+
store
|
|
1637
|
+
);
|
|
1638
|
+
myTransaction == null ? void 0 : myTransaction.subject.next(child.transactionMeta.update);
|
|
1639
|
+
store.logger.info(
|
|
1640
|
+
`\u{1F6EC}`,
|
|
1641
|
+
`transaction`,
|
|
1642
|
+
child.transactionMeta.update.key,
|
|
1643
|
+
`Finished applying transaction.`
|
|
1644
|
+
);
|
|
1645
|
+
} else if (isChildStore(parent)) {
|
|
1646
|
+
parent.transactionMeta.update.updates.push(child.transactionMeta.update);
|
|
1647
|
+
}
|
|
1648
|
+
parent.on.transactionApplying.next(null);
|
|
1649
|
+
};
|
|
1650
|
+
|
|
1651
|
+
// internal/src/transaction/assign-transaction-to-continuity.ts
|
|
1652
|
+
function assignTransactionToContinuity(continuityKey, transactionKey, store) {
|
|
1653
|
+
const isRoot = isRootStore(store);
|
|
1654
|
+
if (!isRoot) {
|
|
1655
|
+
return;
|
|
1656
|
+
}
|
|
1657
|
+
const { epoch, actionContinuities } = store.transactionMeta;
|
|
1658
|
+
actionContinuities.set(continuityKey, transactionKey);
|
|
1659
|
+
if (!epoch.has(continuityKey)) {
|
|
1660
|
+
epoch.set(continuityKey, -1);
|
|
1661
|
+
}
|
|
1662
|
+
}
|
|
1663
|
+
|
|
1664
|
+
// internal/src/lazy-map.ts
|
|
1665
|
+
var LazyMap = class extends Map {
|
|
1666
|
+
constructor(source) {
|
|
1667
|
+
super();
|
|
1668
|
+
this.source = source;
|
|
1669
|
+
this.deleted = /* @__PURE__ */ new Set();
|
|
1670
|
+
}
|
|
1671
|
+
get(key) {
|
|
1672
|
+
const has = super.has(key);
|
|
1673
|
+
if (has) {
|
|
1674
|
+
return super.get(key);
|
|
1675
|
+
}
|
|
1676
|
+
if (!this.deleted.has(key) && this.source.has(key)) {
|
|
1677
|
+
const value = this.source.get(key);
|
|
1678
|
+
return value;
|
|
1679
|
+
}
|
|
1680
|
+
return void 0;
|
|
1681
|
+
}
|
|
1682
|
+
set(key, value) {
|
|
1683
|
+
this.deleted.delete(key);
|
|
1684
|
+
return super.set(key, value);
|
|
1685
|
+
}
|
|
1686
|
+
hasOwn(key) {
|
|
1687
|
+
return super.has(key);
|
|
1688
|
+
}
|
|
1689
|
+
has(key) {
|
|
1690
|
+
return !this.deleted.has(key) && (super.has(key) || this.source.has(key));
|
|
1691
|
+
}
|
|
1692
|
+
delete(key) {
|
|
1693
|
+
this.deleted.add(key);
|
|
1694
|
+
return super.delete(key);
|
|
1695
|
+
}
|
|
1696
|
+
};
|
|
1697
|
+
|
|
1698
|
+
// internal/src/transaction/build-transaction.ts
|
|
1699
|
+
var buildTransaction = (key, params, store, id) => {
|
|
1700
|
+
const parent = newest(store);
|
|
1701
|
+
const childBase = {
|
|
1702
|
+
parent,
|
|
1703
|
+
child: null,
|
|
1704
|
+
on: parent.on,
|
|
1705
|
+
loggers: parent.loggers,
|
|
1706
|
+
logger: parent.logger,
|
|
1707
|
+
config: parent.config,
|
|
1708
|
+
atoms: new LazyMap(parent.atoms),
|
|
1709
|
+
atomsThatAreDefault: new Set(parent.atomsThatAreDefault),
|
|
1710
|
+
families: new LazyMap(parent.families),
|
|
1711
|
+
operation: { open: false },
|
|
1712
|
+
readonlySelectors: new LazyMap(parent.readonlySelectors),
|
|
1713
|
+
timelines: new LazyMap(parent.timelines),
|
|
1714
|
+
timelineTopics: new Junction(parent.timelineTopics.toJSON()),
|
|
1715
|
+
trackers: /* @__PURE__ */ new Map(),
|
|
1716
|
+
transactions: new LazyMap(parent.transactions),
|
|
1717
|
+
selectorAtoms: new Junction(parent.selectorAtoms.toJSON()),
|
|
1718
|
+
selectorGraph: new Junction(parent.selectorGraph.toJSON(), {
|
|
1719
|
+
makeContentKey: (...keys) => keys.sort().join(`:`)
|
|
1720
|
+
}),
|
|
1721
|
+
selectors: new LazyMap(parent.selectors),
|
|
1722
|
+
valueMap: new LazyMap(parent.valueMap),
|
|
1723
|
+
molecules: new LazyMap(parent.molecules),
|
|
1724
|
+
moleculeFamilies: new LazyMap(parent.moleculeFamilies),
|
|
1725
|
+
moleculeInProgress: parent.moleculeInProgress,
|
|
1726
|
+
miscResources: new LazyMap(parent.miscResources)
|
|
1727
|
+
};
|
|
1728
|
+
const epoch = getEpochNumberOfAction(key, store);
|
|
1729
|
+
const transactionMeta = {
|
|
1730
|
+
phase: `building`,
|
|
1731
|
+
update: {
|
|
1732
|
+
type: `transaction_update`,
|
|
1733
|
+
key,
|
|
1734
|
+
id,
|
|
1735
|
+
epoch: epoch === void 0 ? Number.NaN : epoch + 1,
|
|
1736
|
+
updates: [],
|
|
1737
|
+
params,
|
|
1738
|
+
output: void 0
|
|
1739
|
+
},
|
|
1740
|
+
transactors: {
|
|
1741
|
+
get: (token) => getFromStore(token, child),
|
|
1742
|
+
set: (token, value) => {
|
|
1743
|
+
setIntoStore(token, value, child);
|
|
1744
|
+
},
|
|
1745
|
+
run: (token, identifier = arbitrary()) => actUponStore(token, identifier, child),
|
|
1746
|
+
find: (token, k) => findInStore(token, k, child),
|
|
1747
|
+
seek: (token, k) => seekInStore(token, k, child),
|
|
1748
|
+
json: (token) => getJsonToken(token, child),
|
|
1749
|
+
make: (context, family, k, ...args) => makeMoleculeInStore(child, context, family, k, ...args),
|
|
1750
|
+
dispose: (token) => {
|
|
1751
|
+
disposeFromStore(token, child);
|
|
1752
|
+
},
|
|
1753
|
+
env: () => getEnvironmentData(child)
|
|
1754
|
+
}
|
|
1755
|
+
};
|
|
1756
|
+
const child = Object.assign(childBase, {
|
|
1757
|
+
transactionMeta
|
|
1758
|
+
});
|
|
1759
|
+
parent.child = child;
|
|
1760
|
+
store.logger.info(
|
|
1761
|
+
`\u{1F6EB}`,
|
|
1762
|
+
`transaction`,
|
|
1763
|
+
key,
|
|
1764
|
+
`Building transaction with params:`,
|
|
1765
|
+
params
|
|
1766
|
+
);
|
|
1767
|
+
return child;
|
|
1768
|
+
};
|
|
1769
|
+
|
|
1770
|
+
// internal/src/transaction/create-transaction.ts
|
|
1771
|
+
function createTransaction(options, store) {
|
|
1772
|
+
const newTransaction = {
|
|
1773
|
+
key: options.key,
|
|
1774
|
+
type: `transaction`,
|
|
1775
|
+
run: (params, id) => {
|
|
1776
|
+
const childStore = buildTransaction(options.key, params, store, id);
|
|
1777
|
+
try {
|
|
1778
|
+
const target2 = newest(store);
|
|
1779
|
+
const { transactors } = childStore.transactionMeta;
|
|
1780
|
+
const output = options.do(transactors, ...params);
|
|
1781
|
+
applyTransaction(output, target2);
|
|
1782
|
+
return output;
|
|
1783
|
+
} catch (thrown) {
|
|
1784
|
+
abortTransaction(target);
|
|
1785
|
+
store.logger.warn(`\u{1F4A5}`, `transaction`, options.key, `caught:`, thrown);
|
|
1786
|
+
throw thrown;
|
|
1787
|
+
}
|
|
1788
|
+
},
|
|
1789
|
+
install: (s) => createTransaction(options, s),
|
|
1790
|
+
subject: new Subject()
|
|
1791
|
+
};
|
|
1792
|
+
const target = newest(store);
|
|
1793
|
+
target.transactions.set(newTransaction.key, newTransaction);
|
|
1794
|
+
const token = deposit(newTransaction);
|
|
1795
|
+
store.on.transactionCreation.next(token);
|
|
1796
|
+
return token;
|
|
1797
|
+
}
|
|
1798
|
+
|
|
1799
|
+
// internal/src/transaction/get-epoch-number.ts
|
|
1800
|
+
function getContinuityKey(transactionKey, store) {
|
|
1801
|
+
const isRoot = isRootStore(store);
|
|
1802
|
+
const continuity = isRoot ? store.transactionMeta.actionContinuities.getRelatedKey(transactionKey) : void 0;
|
|
1803
|
+
return continuity;
|
|
1804
|
+
}
|
|
1805
|
+
function getEpochNumberOfContinuity(continuityKey, store) {
|
|
1806
|
+
const isRoot = isRootStore(store);
|
|
1807
|
+
const epoch = isRoot && continuityKey ? store.transactionMeta.epoch.get(continuityKey) : void 0;
|
|
1808
|
+
return epoch;
|
|
1809
|
+
}
|
|
1810
|
+
function getEpochNumberOfAction(transactionKey, store) {
|
|
1811
|
+
const isRoot = isRootStore(store);
|
|
1812
|
+
const continuity = isRoot ? store.transactionMeta.actionContinuities.getRelatedKey(transactionKey) : void 0;
|
|
1813
|
+
const epoch = isRoot && continuity !== void 0 ? store.transactionMeta.epoch.get(continuity) : void 0;
|
|
1814
|
+
return epoch;
|
|
1815
|
+
}
|
|
1816
|
+
|
|
1817
|
+
// internal/src/transaction/index.ts
|
|
1818
|
+
var TRANSACTION_PHASES = [`idle`, `building`, `applying`];
|
|
1819
|
+
|
|
1820
|
+
// internal/src/store/store.ts
|
|
1821
|
+
var Store = class {
|
|
1822
|
+
constructor(config, store = null) {
|
|
1823
|
+
this.parent = null;
|
|
1824
|
+
this.child = null;
|
|
1825
|
+
this.valueMap = /* @__PURE__ */ new Map();
|
|
1826
|
+
this.atoms = /* @__PURE__ */ new Map();
|
|
1827
|
+
this.selectors = /* @__PURE__ */ new Map();
|
|
1828
|
+
this.readonlySelectors = /* @__PURE__ */ new Map();
|
|
1829
|
+
this.atomsThatAreDefault = /* @__PURE__ */ new Set();
|
|
1830
|
+
this.selectorAtoms = new Junction({
|
|
1831
|
+
between: [`selectorKey`, `atomKey`],
|
|
1832
|
+
cardinality: `n:n`
|
|
1833
|
+
});
|
|
1834
|
+
this.selectorGraph = new Junction(
|
|
1835
|
+
{
|
|
1836
|
+
between: [`upstreamSelectorKey`, `downstreamSelectorKey`],
|
|
1837
|
+
cardinality: `n:n`
|
|
1838
|
+
},
|
|
1839
|
+
{
|
|
1840
|
+
makeContentKey: (...keys) => keys.sort().join(`:`)
|
|
1841
|
+
}
|
|
1842
|
+
);
|
|
1843
|
+
this.trackers = /* @__PURE__ */ new Map();
|
|
1844
|
+
this.families = /* @__PURE__ */ new Map();
|
|
1845
|
+
this.transactions = /* @__PURE__ */ new Map();
|
|
1846
|
+
this.transactionMeta = {
|
|
1847
|
+
epoch: /* @__PURE__ */ new Map(),
|
|
1848
|
+
actionContinuities: new Junction({
|
|
1849
|
+
between: [`continuity`, `action`],
|
|
1850
|
+
cardinality: `1:n`
|
|
1851
|
+
})
|
|
1852
|
+
};
|
|
1853
|
+
this.timelines = /* @__PURE__ */ new Map();
|
|
1854
|
+
this.timelineTopics = new Junction({
|
|
1855
|
+
between: [`timelineKey`, `topicKey`],
|
|
1856
|
+
cardinality: `1:n`
|
|
1857
|
+
});
|
|
1858
|
+
this.molecules = /* @__PURE__ */ new Map();
|
|
1859
|
+
this.moleculeFamilies = /* @__PURE__ */ new Map();
|
|
1860
|
+
this.moleculeInProgress = null;
|
|
1861
|
+
this.miscResources = /* @__PURE__ */ new Map();
|
|
1862
|
+
this.on = {
|
|
1863
|
+
atomCreation: new Subject(),
|
|
1864
|
+
atomDisposal: new Subject(),
|
|
1865
|
+
selectorCreation: new Subject(),
|
|
1866
|
+
selectorDisposal: new Subject(),
|
|
1867
|
+
timelineCreation: new Subject(),
|
|
1868
|
+
transactionCreation: new Subject(),
|
|
1869
|
+
transactionApplying: new StatefulSubject(
|
|
1870
|
+
null
|
|
1871
|
+
),
|
|
1872
|
+
operationClose: new Subject(),
|
|
1873
|
+
moleculeCreationStart: new Subject(),
|
|
1874
|
+
moleculeCreationDone: new Subject(),
|
|
1875
|
+
moleculeDisposal: new Subject()
|
|
1876
|
+
};
|
|
1877
|
+
this.operation = { open: false };
|
|
1878
|
+
this.config = {
|
|
1879
|
+
name: `IMPLICIT_STORE`,
|
|
1880
|
+
lifespan: `ephemeral`
|
|
1881
|
+
};
|
|
1882
|
+
this.loggers = [
|
|
1883
|
+
new atom_io.AtomIOLogger(`warn`, (_, __, key) => !key.includes(`\u{1F441}\u200D\u{1F5E8}`))
|
|
1884
|
+
];
|
|
1885
|
+
this.logger = {
|
|
1886
|
+
error: (...messages) => {
|
|
1887
|
+
for (const logger of this.loggers) logger.error(...messages);
|
|
1888
|
+
},
|
|
1889
|
+
info: (...messages) => {
|
|
1890
|
+
for (const logger of this.loggers) logger.info(...messages);
|
|
1891
|
+
},
|
|
1892
|
+
warn: (...messages) => {
|
|
1893
|
+
for (const logger of this.loggers) logger.warn(...messages);
|
|
1894
|
+
}
|
|
1895
|
+
};
|
|
1896
|
+
if (store !== null) {
|
|
1897
|
+
this.valueMap = new Map(store == null ? void 0 : store.valueMap);
|
|
1898
|
+
this.operation = __spreadValues({}, store == null ? void 0 : store.operation);
|
|
1899
|
+
if (isRootStore(store)) {
|
|
1900
|
+
this.transactionMeta = {
|
|
1901
|
+
epoch: new Map(store == null ? void 0 : store.transactionMeta.epoch),
|
|
1902
|
+
actionContinuities: new Junction(
|
|
1903
|
+
store == null ? void 0 : store.transactionMeta.actionContinuities.toJSON()
|
|
1904
|
+
)
|
|
1905
|
+
};
|
|
1906
|
+
}
|
|
1907
|
+
this.config = __spreadValues(__spreadValues({}, store == null ? void 0 : store.config), config);
|
|
1908
|
+
for (const [, family] of store.families) {
|
|
1909
|
+
family.install(this);
|
|
1910
|
+
}
|
|
1911
|
+
const mutableHelpers = /* @__PURE__ */ new Set();
|
|
1912
|
+
for (const [, atom] of store.atoms) {
|
|
1913
|
+
if (mutableHelpers.has(atom.key)) {
|
|
1914
|
+
continue;
|
|
1942
1915
|
}
|
|
1916
|
+
atom.install(this);
|
|
1917
|
+
if (atom.type === `mutable_atom`) {
|
|
1918
|
+
const originalJsonToken = getJsonToken(atom, store);
|
|
1919
|
+
const originalUpdateToken = getUpdateToken(atom);
|
|
1920
|
+
mutableHelpers.add(originalJsonToken.key);
|
|
1921
|
+
mutableHelpers.add(originalUpdateToken.key);
|
|
1922
|
+
}
|
|
1923
|
+
}
|
|
1924
|
+
for (const [, selector] of store.readonlySelectors) {
|
|
1925
|
+
selector.install(this);
|
|
1926
|
+
}
|
|
1927
|
+
for (const [, selector] of store.selectors) {
|
|
1928
|
+
if (mutableHelpers.has(selector.key)) {
|
|
1929
|
+
continue;
|
|
1930
|
+
}
|
|
1931
|
+
selector.install(this);
|
|
1932
|
+
}
|
|
1933
|
+
for (const [, tx] of store.transactions) {
|
|
1934
|
+
tx.install(this);
|
|
1935
|
+
}
|
|
1936
|
+
for (const [, timeline] of store.timelines) {
|
|
1937
|
+
timeline.install(this);
|
|
1938
|
+
}
|
|
1939
|
+
}
|
|
1940
|
+
}
|
|
1941
|
+
};
|
|
1942
|
+
var IMPLICIT = {
|
|
1943
|
+
STORE_INTERNAL: void 0,
|
|
1944
|
+
get STORE() {
|
|
1945
|
+
var _a;
|
|
1946
|
+
return (_a = this.STORE_INTERNAL) != null ? _a : this.STORE_INTERNAL = new Store({
|
|
1947
|
+
name: `IMPLICIT_STORE`,
|
|
1948
|
+
lifespan: `ephemeral`
|
|
1949
|
+
});
|
|
1950
|
+
}
|
|
1951
|
+
};
|
|
1952
|
+
var clearStore = (store) => {
|
|
1953
|
+
const { config } = store;
|
|
1954
|
+
for (const disposable of store.miscResources.values()) {
|
|
1955
|
+
disposable[Symbol.dispose]();
|
|
1956
|
+
}
|
|
1957
|
+
Object.assign(store, new Store(config));
|
|
1958
|
+
store.config = config;
|
|
1959
|
+
};
|
|
1960
|
+
function withdraw(token, store) {
|
|
1961
|
+
let withdrawn;
|
|
1962
|
+
let target = store;
|
|
1963
|
+
while (target !== null) {
|
|
1964
|
+
switch (token.type) {
|
|
1965
|
+
case `atom`:
|
|
1966
|
+
case `mutable_atom`:
|
|
1967
|
+
withdrawn = target.atoms.get(token.key);
|
|
1968
|
+
break;
|
|
1969
|
+
case `selector`:
|
|
1970
|
+
withdrawn = target.selectors.get(token.key);
|
|
1971
|
+
break;
|
|
1972
|
+
case `readonly_selector`:
|
|
1973
|
+
withdrawn = target.readonlySelectors.get(token.key);
|
|
1974
|
+
break;
|
|
1975
|
+
case `atom_family`:
|
|
1976
|
+
case `mutable_atom_family`:
|
|
1977
|
+
case `selector_family`:
|
|
1978
|
+
case `readonly_selector_family`:
|
|
1979
|
+
withdrawn = target.families.get(token.key);
|
|
1980
|
+
break;
|
|
1981
|
+
case `timeline`:
|
|
1982
|
+
withdrawn = target.timelines.get(token.key);
|
|
1983
|
+
break;
|
|
1984
|
+
case `transaction`:
|
|
1985
|
+
withdrawn = target.transactions.get(token.key);
|
|
1943
1986
|
break;
|
|
1944
|
-
case `
|
|
1945
|
-
|
|
1946
|
-
|
|
1947
|
-
|
|
1948
|
-
|
|
1949
|
-
store
|
|
1950
|
-
);
|
|
1951
|
-
family.subject.next({
|
|
1952
|
-
type: `state_disposal`,
|
|
1953
|
-
token: selectorToken
|
|
1954
|
-
});
|
|
1955
|
-
}
|
|
1987
|
+
case `molecule`:
|
|
1988
|
+
withdrawn = target.molecules.get(json.stringifyJson(token.key));
|
|
1989
|
+
break;
|
|
1990
|
+
case `molecule_family`:
|
|
1991
|
+
withdrawn = target.moleculeFamilies.get(token.key);
|
|
1956
1992
|
break;
|
|
1957
1993
|
}
|
|
1958
|
-
|
|
1959
|
-
|
|
1960
|
-
const downstreamTokens = target.selectorGraph.getRelationEntries({ upstreamSelectorKey: key }).filter(([_, { source }]) => source === key).map(
|
|
1961
|
-
([downstreamSelectorKey]) => {
|
|
1962
|
-
var _a2;
|
|
1963
|
-
return (_a2 = target.selectors.get(downstreamSelectorKey)) != null ? _a2 : target.readonlySelectors.get(downstreamSelectorKey);
|
|
1964
|
-
}
|
|
1965
|
-
);
|
|
1966
|
-
for (const downstreamToken of downstreamTokens) {
|
|
1967
|
-
if (downstreamToken) {
|
|
1968
|
-
disposeSelector(downstreamToken, store);
|
|
1969
|
-
}
|
|
1970
|
-
}
|
|
1971
|
-
target.selectorGraph.delete(key);
|
|
1972
|
-
store.logger.info(`\u{1F525}`, selectorToken.type, key, `deleted`);
|
|
1973
|
-
if (isChildStore(target) && target.transactionMeta.phase === `building`) {
|
|
1974
|
-
target.transactionMeta.update.updates.push({
|
|
1975
|
-
type: `state_disposal`,
|
|
1976
|
-
token: selectorToken
|
|
1977
|
-
});
|
|
1978
|
-
} else {
|
|
1979
|
-
store.on.selectorDisposal.next(selectorToken);
|
|
1994
|
+
if (withdrawn) {
|
|
1995
|
+
return withdrawn;
|
|
1980
1996
|
}
|
|
1997
|
+
target = target.child;
|
|
1981
1998
|
}
|
|
1999
|
+
throw new NotFoundError(token, store);
|
|
1982
2000
|
}
|
|
1983
2001
|
|
|
1984
2002
|
// internal/src/subscribe/recall-state.ts
|
|
@@ -2175,7 +2193,7 @@ var Tracker = class {
|
|
|
2175
2193
|
subscribeToState(
|
|
2176
2194
|
latestUpdateState,
|
|
2177
2195
|
({ newValue, oldValue }) => {
|
|
2178
|
-
const timelineId = target.
|
|
2196
|
+
const timelineId = target.timelineTopics.getRelatedKey(
|
|
2179
2197
|
latestUpdateState.key
|
|
2180
2198
|
);
|
|
2181
2199
|
if (timelineId) {
|
|
@@ -2626,6 +2644,10 @@ function disposeAtom(atomToken, store) {
|
|
|
2626
2644
|
token: atomToken,
|
|
2627
2645
|
value: lastValue
|
|
2628
2646
|
});
|
|
2647
|
+
const molecule = target.molecules.get(atom.family.subKey);
|
|
2648
|
+
if (molecule) {
|
|
2649
|
+
molecule.tokens.delete(key);
|
|
2650
|
+
}
|
|
2629
2651
|
target.atoms.delete(key);
|
|
2630
2652
|
target.valueMap.delete(key);
|
|
2631
2653
|
const selectorKeys = target.selectorAtoms.getRelatedKeys(key);
|
|
@@ -2639,7 +2661,7 @@ function disposeAtom(atomToken, store) {
|
|
|
2639
2661
|
}
|
|
2640
2662
|
target.selectorAtoms.delete(key);
|
|
2641
2663
|
target.atomsThatAreDefault.delete(key);
|
|
2642
|
-
target.
|
|
2664
|
+
target.timelineTopics.delete(key);
|
|
2643
2665
|
if (atomToken.type === `mutable_atom`) {
|
|
2644
2666
|
const updateToken = getUpdateToken(atomToken);
|
|
2645
2667
|
disposeAtom(updateToken, store);
|
|
@@ -2656,26 +2678,123 @@ function disposeAtom(atomToken, store) {
|
|
|
2656
2678
|
}
|
|
2657
2679
|
}
|
|
2658
2680
|
}
|
|
2659
|
-
|
|
2660
|
-
|
|
2661
|
-
|
|
2681
|
+
function createTimeline(options, store, data) {
|
|
2682
|
+
var _a;
|
|
2683
|
+
const tl = __spreadProps(__spreadValues({
|
|
2684
|
+
type: `timeline`,
|
|
2685
|
+
key: options.key,
|
|
2686
|
+
at: 0,
|
|
2687
|
+
timeTraveling: null,
|
|
2688
|
+
selectorTime: null,
|
|
2689
|
+
transactionKey: null
|
|
2690
|
+
}, data), {
|
|
2691
|
+
history: (_a = data == null ? void 0 : data.history.map((update) => __spreadValues({}, update))) != null ? _a : [],
|
|
2692
|
+
install: (s) => createTimeline(options, s, tl),
|
|
2693
|
+
subject: new Subject(),
|
|
2694
|
+
subscriptions: /* @__PURE__ */ new Map()
|
|
2695
|
+
});
|
|
2696
|
+
if (options.shouldCapture) {
|
|
2697
|
+
tl.shouldCapture = options.shouldCapture;
|
|
2698
|
+
}
|
|
2699
|
+
const timelineKey = options.key;
|
|
2700
|
+
const target = newest(store);
|
|
2701
|
+
for (const initialTopic of options.scope) {
|
|
2702
|
+
switch (initialTopic.type) {
|
|
2703
|
+
case `atom`:
|
|
2704
|
+
case `mutable_atom`:
|
|
2705
|
+
{
|
|
2706
|
+
const atomToken = initialTopic;
|
|
2707
|
+
const atomKey = atomToken.key;
|
|
2708
|
+
let existingTimelineKey = target.timelineTopics.getRelatedKey(atomKey);
|
|
2709
|
+
if (`family` in atomToken) {
|
|
2710
|
+
const familyKey = atomToken.family.key;
|
|
2711
|
+
existingTimelineKey = target.timelineTopics.getRelatedKey(familyKey);
|
|
2712
|
+
if (existingTimelineKey) {
|
|
2713
|
+
store.logger.error(
|
|
2714
|
+
`\u274C`,
|
|
2715
|
+
`timeline`,
|
|
2716
|
+
options.key,
|
|
2717
|
+
`Failed to add atom "${atomKey}" because its family "${familyKey}" already belongs to timeline "${existingTimelineKey}"`
|
|
2718
|
+
);
|
|
2719
|
+
continue;
|
|
2720
|
+
}
|
|
2721
|
+
}
|
|
2722
|
+
if (existingTimelineKey) {
|
|
2723
|
+
store.logger.error(
|
|
2724
|
+
`\u274C`,
|
|
2725
|
+
`timeline`,
|
|
2726
|
+
options.key,
|
|
2727
|
+
`Failed to add atom "${atomKey}" because it already belongs to timeline "${existingTimelineKey}"`
|
|
2728
|
+
);
|
|
2729
|
+
continue;
|
|
2730
|
+
}
|
|
2731
|
+
addAtomToTimeline(atomToken, tl, store);
|
|
2732
|
+
}
|
|
2733
|
+
break;
|
|
2734
|
+
case `atom_family`:
|
|
2735
|
+
case `mutable_atom_family`:
|
|
2736
|
+
{
|
|
2737
|
+
const familyToken = initialTopic;
|
|
2738
|
+
const familyKey = familyToken.key;
|
|
2739
|
+
const existingTimelineKey = target.timelineTopics.getRelatedKey(familyKey);
|
|
2740
|
+
if (existingTimelineKey) {
|
|
2741
|
+
store.logger.error(
|
|
2742
|
+
`\u274C`,
|
|
2743
|
+
`timeline`,
|
|
2744
|
+
options.key,
|
|
2745
|
+
`Failed to add atom family "${familyKey}" because it already belongs to timeline "${existingTimelineKey}"`
|
|
2746
|
+
);
|
|
2747
|
+
continue;
|
|
2748
|
+
}
|
|
2749
|
+
addAtomFamilyToTimeline(familyToken, tl, store);
|
|
2750
|
+
}
|
|
2751
|
+
break;
|
|
2752
|
+
case `molecule_family`:
|
|
2753
|
+
{
|
|
2754
|
+
const familyToken = initialTopic;
|
|
2755
|
+
const familyKey = familyToken.key;
|
|
2756
|
+
const existingTimelineKey = target.timelineTopics.getRelatedKey(familyKey);
|
|
2757
|
+
if (existingTimelineKey) {
|
|
2758
|
+
store.logger.error(
|
|
2759
|
+
`\u274C`,
|
|
2760
|
+
`timeline`,
|
|
2761
|
+
options.key,
|
|
2762
|
+
`Failed to add molecule family "${familyKey}" because it already belongs to timeline "${existingTimelineKey}"`
|
|
2763
|
+
);
|
|
2764
|
+
continue;
|
|
2765
|
+
}
|
|
2766
|
+
addMoleculeFamilyToTimeline(familyToken, tl, store);
|
|
2767
|
+
}
|
|
2768
|
+
break;
|
|
2769
|
+
}
|
|
2770
|
+
}
|
|
2771
|
+
store.timelines.set(options.key, tl);
|
|
2772
|
+
const token = {
|
|
2773
|
+
key: timelineKey,
|
|
2774
|
+
type: `timeline`
|
|
2775
|
+
};
|
|
2776
|
+
store.on.timelineCreation.next(token);
|
|
2777
|
+
return token;
|
|
2778
|
+
}
|
|
2779
|
+
function addAtomToTimeline(atomToken, tl, store) {
|
|
2662
2780
|
let maybeAtom = withdraw(atomToken, store);
|
|
2663
2781
|
if (maybeAtom.type === `mutable_atom`) {
|
|
2664
2782
|
const updateToken = getUpdateToken(maybeAtom);
|
|
2665
2783
|
maybeAtom = withdraw(updateToken, store);
|
|
2666
2784
|
}
|
|
2667
2785
|
const atom = maybeAtom;
|
|
2668
|
-
store.
|
|
2786
|
+
store.timelineTopics.set(
|
|
2787
|
+
{ topicKey: atom.key, timelineKey: tl.key },
|
|
2788
|
+
{ topicType: `atom` }
|
|
2789
|
+
);
|
|
2669
2790
|
tl.subscriptions.set(
|
|
2670
2791
|
atom.key,
|
|
2671
2792
|
atom.subject.subscribe(`timeline`, (update) => {
|
|
2672
|
-
var _a, _b, _c, _d, _e
|
|
2793
|
+
var _a, _b, _c, _d, _e;
|
|
2673
2794
|
const target = newest(store);
|
|
2674
2795
|
const currentSelectorKey = store.operation.open && store.operation.token.type === `selector` ? store.operation.token.key : null;
|
|
2675
2796
|
const currentSelectorTime = store.operation.open && store.operation.token.type === `selector` ? store.operation.time : null;
|
|
2676
|
-
const
|
|
2677
|
-
const currentTransactionKey = (_a = transactionApplying.state) == null ? void 0 : _a.update.key;
|
|
2678
|
-
const currentTransactionInstanceId = (_b = transactionApplying.state) == null ? void 0 : _b.update.id;
|
|
2797
|
+
const txUpdateInProgress = (_a = target.on.transactionApplying.state) == null ? void 0 : _a.update;
|
|
2679
2798
|
store.logger.info(
|
|
2680
2799
|
`\u23F3`,
|
|
2681
2800
|
`timeline`,
|
|
@@ -2686,109 +2805,11 @@ var addAtomToTimeline = (atomToken, tl, store) => {
|
|
|
2686
2805
|
update.oldValue,
|
|
2687
2806
|
`->`,
|
|
2688
2807
|
update.newValue,
|
|
2689
|
-
|
|
2808
|
+
txUpdateInProgress ? `in transaction "${txUpdateInProgress.key}"` : currentSelectorKey ? `in selector "${currentSelectorKey}"` : ``
|
|
2690
2809
|
);
|
|
2691
2810
|
if (tl.timeTraveling === null) {
|
|
2692
|
-
if (
|
|
2693
|
-
|
|
2694
|
-
if (mostRecentUpdate === void 0) {
|
|
2695
|
-
throw new Error(
|
|
2696
|
-
`Timeline "${tl.key}" has a selectorTime, but no history. This is most likely a bug in AtomIO.`
|
|
2697
|
-
);
|
|
2698
|
-
}
|
|
2699
|
-
}
|
|
2700
|
-
if (currentTransactionKey) {
|
|
2701
|
-
const txToken = {
|
|
2702
|
-
key: currentTransactionKey,
|
|
2703
|
-
type: `transaction`
|
|
2704
|
-
};
|
|
2705
|
-
const currentTransaction = withdraw(txToken, store);
|
|
2706
|
-
if (tl.transactionKey !== currentTransactionKey) {
|
|
2707
|
-
if (tl.transactionKey) {
|
|
2708
|
-
store.logger.error(
|
|
2709
|
-
`\u{1F41E}`,
|
|
2710
|
-
`timeline`,
|
|
2711
|
-
tl.key,
|
|
2712
|
-
`unable to resolve transaction "${tl.transactionKey}. This is probably a bug in AtomIO.`
|
|
2713
|
-
);
|
|
2714
|
-
}
|
|
2715
|
-
tl.transactionKey = currentTransactionKey;
|
|
2716
|
-
const unsubscribe = currentTransaction.subject.subscribe(
|
|
2717
|
-
`timeline:${tl.key}`,
|
|
2718
|
-
(transactionUpdate) => {
|
|
2719
|
-
var _a2, _b2;
|
|
2720
|
-
unsubscribe();
|
|
2721
|
-
if (tl.timeTraveling === null && currentTransactionInstanceId) {
|
|
2722
|
-
if (tl.at !== tl.history.length) {
|
|
2723
|
-
tl.history.splice(tl.at);
|
|
2724
|
-
}
|
|
2725
|
-
const filterUpdates = (updates2) => updates2.filter((updateFromTx) => {
|
|
2726
|
-
var _a3, _b3;
|
|
2727
|
-
const newestStore = newest(store);
|
|
2728
|
-
if (`updates` in updateFromTx) {
|
|
2729
|
-
return true;
|
|
2730
|
-
}
|
|
2731
|
-
const atomOrFamilyKeys = newestStore.timelineAtoms.getRelatedKeys(tl.key);
|
|
2732
|
-
if (!atomOrFamilyKeys) {
|
|
2733
|
-
return false;
|
|
2734
|
-
}
|
|
2735
|
-
let key;
|
|
2736
|
-
let familyKey;
|
|
2737
|
-
switch (updateFromTx.type) {
|
|
2738
|
-
case `state_creation`:
|
|
2739
|
-
case `state_disposal`:
|
|
2740
|
-
key = updateFromTx.token.key;
|
|
2741
|
-
familyKey = (_a3 = updateFromTx.token.family) == null ? void 0 : _a3.key;
|
|
2742
|
-
break;
|
|
2743
|
-
case `molecule_creation`:
|
|
2744
|
-
case `molecule_disposal`:
|
|
2745
|
-
break;
|
|
2746
|
-
default:
|
|
2747
|
-
key = updateFromTx.key;
|
|
2748
|
-
familyKey = (_b3 = updateFromTx.family) == null ? void 0 : _b3.key;
|
|
2749
|
-
break;
|
|
2750
|
-
}
|
|
2751
|
-
if (key === void 0) {
|
|
2752
|
-
return false;
|
|
2753
|
-
}
|
|
2754
|
-
if (atomOrFamilyKeys.has(key)) {
|
|
2755
|
-
return true;
|
|
2756
|
-
}
|
|
2757
|
-
if (familyKey !== void 0) {
|
|
2758
|
-
return atomOrFamilyKeys.has(familyKey);
|
|
2759
|
-
}
|
|
2760
|
-
return false;
|
|
2761
|
-
}).map((updateFromTx) => {
|
|
2762
|
-
if (`updates` in updateFromTx) {
|
|
2763
|
-
return __spreadProps(__spreadValues({}, updateFromTx), {
|
|
2764
|
-
updates: filterUpdates(updateFromTx.updates)
|
|
2765
|
-
});
|
|
2766
|
-
}
|
|
2767
|
-
return updateFromTx;
|
|
2768
|
-
});
|
|
2769
|
-
const updates = filterUpdates(transactionUpdate.updates);
|
|
2770
|
-
const timelineTransactionUpdate = __spreadProps(__spreadValues({
|
|
2771
|
-
timestamp: Date.now()
|
|
2772
|
-
}, transactionUpdate), {
|
|
2773
|
-
updates
|
|
2774
|
-
});
|
|
2775
|
-
const willCapture = (_b2 = (_a2 = tl.shouldCapture) == null ? void 0 : _a2.call(tl, timelineTransactionUpdate, tl)) != null ? _b2 : true;
|
|
2776
|
-
if (willCapture) {
|
|
2777
|
-
tl.history.push(timelineTransactionUpdate);
|
|
2778
|
-
tl.at = tl.history.length;
|
|
2779
|
-
tl.subject.next(timelineTransactionUpdate);
|
|
2780
|
-
}
|
|
2781
|
-
}
|
|
2782
|
-
tl.transactionKey = null;
|
|
2783
|
-
store.logger.info(
|
|
2784
|
-
`\u231B`,
|
|
2785
|
-
`timeline`,
|
|
2786
|
-
tl.key,
|
|
2787
|
-
`got a transaction_update "${transactionUpdate.key}"`
|
|
2788
|
-
);
|
|
2789
|
-
}
|
|
2790
|
-
);
|
|
2791
|
-
}
|
|
2811
|
+
if (txUpdateInProgress) {
|
|
2812
|
+
joinTransaction(tl, txUpdateInProgress, store);
|
|
2792
2813
|
} else if (currentSelectorKey && currentSelectorTime) {
|
|
2793
2814
|
let latestUpdate = tl.history.at(-1);
|
|
2794
2815
|
if (currentSelectorTime !== tl.selectorTime) {
|
|
@@ -2831,7 +2852,7 @@ var addAtomToTimeline = (atomToken, tl, store) => {
|
|
|
2831
2852
|
}
|
|
2832
2853
|
}
|
|
2833
2854
|
if (latestUpdate) {
|
|
2834
|
-
const willCaptureSelectorUpdate = (
|
|
2855
|
+
const willCaptureSelectorUpdate = (_c = (_b = tl.shouldCapture) == null ? void 0 : _b.call(tl, latestUpdate, tl)) != null ? _c : true;
|
|
2835
2856
|
if (willCaptureSelectorUpdate) {
|
|
2836
2857
|
tl.subject.next(latestUpdate);
|
|
2837
2858
|
} else {
|
|
@@ -2855,7 +2876,7 @@ var addAtomToTimeline = (atomToken, tl, store) => {
|
|
|
2855
2876
|
if (atom.family) {
|
|
2856
2877
|
atomUpdate.family = atom.family;
|
|
2857
2878
|
}
|
|
2858
|
-
const willCapture = (
|
|
2879
|
+
const willCapture = (_e = (_d = tl.shouldCapture) == null ? void 0 : _d.call(tl, atomUpdate, tl)) != null ? _e : true;
|
|
2859
2880
|
store.logger.info(
|
|
2860
2881
|
`\u231B`,
|
|
2861
2882
|
`timeline`,
|
|
@@ -2871,181 +2892,207 @@ var addAtomToTimeline = (atomToken, tl, store) => {
|
|
|
2871
2892
|
}
|
|
2872
2893
|
})
|
|
2873
2894
|
);
|
|
2874
|
-
}
|
|
2875
|
-
function
|
|
2876
|
-
var _a
|
|
2877
|
-
const
|
|
2878
|
-
|
|
2879
|
-
key:
|
|
2880
|
-
|
|
2881
|
-
|
|
2882
|
-
|
|
2883
|
-
|
|
2884
|
-
|
|
2885
|
-
|
|
2886
|
-
|
|
2887
|
-
|
|
2888
|
-
|
|
2889
|
-
|
|
2890
|
-
|
|
2891
|
-
|
|
2895
|
+
}
|
|
2896
|
+
function addAtomFamilyToTimeline(atomFamilyToken, tl, store) {
|
|
2897
|
+
var _a;
|
|
2898
|
+
const family = withdraw(atomFamilyToken, store);
|
|
2899
|
+
store.timelineTopics.set(
|
|
2900
|
+
{ topicKey: family.key, timelineKey: tl.key },
|
|
2901
|
+
{ topicType: `atom_family` }
|
|
2902
|
+
);
|
|
2903
|
+
tl.subscriptions.set(
|
|
2904
|
+
family.key,
|
|
2905
|
+
family.subject.subscribe(`timeline`, (creationOrDisposal) => {
|
|
2906
|
+
handleStateLifecycleEvent(creationOrDisposal, tl, store);
|
|
2907
|
+
})
|
|
2908
|
+
);
|
|
2909
|
+
for (const atom of store.atoms.values()) {
|
|
2910
|
+
if (((_a = atom.family) == null ? void 0 : _a.key) === family.key) {
|
|
2911
|
+
addAtomToTimeline(atom, tl, store);
|
|
2912
|
+
}
|
|
2892
2913
|
}
|
|
2893
|
-
|
|
2894
|
-
|
|
2895
|
-
|
|
2896
|
-
|
|
2897
|
-
|
|
2898
|
-
|
|
2899
|
-
|
|
2900
|
-
|
|
2901
|
-
|
|
2902
|
-
|
|
2903
|
-
|
|
2904
|
-
|
|
2905
|
-
|
|
2906
|
-
|
|
2907
|
-
|
|
2908
|
-
|
|
2909
|
-
|
|
2910
|
-
|
|
2914
|
+
}
|
|
2915
|
+
function addMoleculeFamilyToTimeline(familyToken, tl, store) {
|
|
2916
|
+
store.timelineTopics.set(
|
|
2917
|
+
{ topicKey: familyToken.key, timelineKey: tl.key },
|
|
2918
|
+
{ topicType: `molecule_family` }
|
|
2919
|
+
);
|
|
2920
|
+
const family = store.moleculeFamilies.get(familyToken.key);
|
|
2921
|
+
if (family) {
|
|
2922
|
+
tl.subscriptions.set(
|
|
2923
|
+
familyToken.key,
|
|
2924
|
+
family.subject.subscribe(`timeline:${tl.key}`, (creationOrDisposal) => {
|
|
2925
|
+
var _a, _b, _c, _d;
|
|
2926
|
+
store.logger.info(
|
|
2927
|
+
`\u{1F41E}`,
|
|
2928
|
+
`timeline`,
|
|
2929
|
+
tl.key,
|
|
2930
|
+
`got a molecule creation or disposal`,
|
|
2931
|
+
creationOrDisposal
|
|
2932
|
+
);
|
|
2933
|
+
switch (creationOrDisposal.type) {
|
|
2934
|
+
case `molecule_creation`:
|
|
2935
|
+
{
|
|
2936
|
+
store.timelineTopics.set(
|
|
2937
|
+
{
|
|
2938
|
+
topicKey: creationOrDisposal.token.key,
|
|
2939
|
+
timelineKey: tl.key
|
|
2940
|
+
},
|
|
2941
|
+
{ topicType: `molecule` }
|
|
2942
|
+
);
|
|
2943
|
+
const txUpdateInProgress = (_a = newest(store).on.transactionApplying.state) == null ? void 0 : _a.update;
|
|
2944
|
+
if (txUpdateInProgress) {
|
|
2945
|
+
joinTransaction(tl, txUpdateInProgress, store);
|
|
2946
|
+
} else if (tl.timeTraveling === null) {
|
|
2947
|
+
const event = Object.assign(creationOrDisposal, {
|
|
2948
|
+
timestamp: Date.now()
|
|
2949
|
+
});
|
|
2950
|
+
tl.history.push(event);
|
|
2951
|
+
tl.at = tl.history.length;
|
|
2952
|
+
tl.subject.next(event);
|
|
2911
2953
|
}
|
|
2912
|
-
|
|
2913
|
-
|
|
2914
|
-
|
|
2915
|
-
|
|
2916
|
-
|
|
2917
|
-
|
|
2918
|
-
|
|
2919
|
-
|
|
2920
|
-
|
|
2921
|
-
|
|
2922
|
-
|
|
2923
|
-
|
|
2924
|
-
|
|
2925
|
-
|
|
2926
|
-
|
|
2927
|
-
|
|
2928
|
-
|
|
2929
|
-
}
|
|
2930
|
-
if (`family` in atom) {
|
|
2931
|
-
const familyTimelineKey = target.timelineAtoms.getRelatedKey(
|
|
2932
|
-
atom.family.key
|
|
2933
|
-
);
|
|
2934
|
-
if (familyTimelineKey) {
|
|
2935
|
-
store.logger.error(
|
|
2936
|
-
`\u274C`,
|
|
2937
|
-
`timeline`,
|
|
2938
|
-
options.key,
|
|
2939
|
-
`Failed to add atom "${atom.key}" because its family "${atom.family.key}" already belongs to timeline "${familyTimelineKey}"`
|
|
2954
|
+
const molecule = withdraw(creationOrDisposal.token, store);
|
|
2955
|
+
for (const token of molecule.tokens.values()) {
|
|
2956
|
+
switch (token.type) {
|
|
2957
|
+
case `atom`:
|
|
2958
|
+
case `mutable_atom`:
|
|
2959
|
+
addAtomToTimeline(token, tl, store);
|
|
2960
|
+
break;
|
|
2961
|
+
}
|
|
2962
|
+
}
|
|
2963
|
+
tl.subscriptions.set(
|
|
2964
|
+
molecule.key,
|
|
2965
|
+
molecule.subject.subscribe(
|
|
2966
|
+
`timeline:${tl.key}`,
|
|
2967
|
+
(stateCreationOrDisposal) => {
|
|
2968
|
+
handleStateLifecycleEvent(stateCreationOrDisposal, tl, store);
|
|
2969
|
+
}
|
|
2970
|
+
)
|
|
2940
2971
|
);
|
|
2941
|
-
continue;
|
|
2942
2972
|
}
|
|
2973
|
+
break;
|
|
2974
|
+
case `molecule_disposal`:
|
|
2975
|
+
{
|
|
2976
|
+
const txUpdateInProgress = (_b = newest(store).on.transactionApplying.state) == null ? void 0 : _b.update;
|
|
2977
|
+
if (txUpdateInProgress) {
|
|
2978
|
+
joinTransaction(tl, txUpdateInProgress, store);
|
|
2979
|
+
} else if (tl.timeTraveling === null) {
|
|
2980
|
+
const event = Object.assign(creationOrDisposal, {
|
|
2981
|
+
timestamp: Date.now()
|
|
2982
|
+
});
|
|
2983
|
+
tl.history.push(event);
|
|
2984
|
+
tl.at = tl.history.length;
|
|
2985
|
+
tl.subject.next(event);
|
|
2986
|
+
}
|
|
2987
|
+
const moleculeKey = creationOrDisposal.token.key;
|
|
2988
|
+
(_c = tl.subscriptions.get(moleculeKey)) == null ? void 0 : _c();
|
|
2989
|
+
tl.subscriptions.delete(moleculeKey);
|
|
2990
|
+
for (const [familyKey] of creationOrDisposal.values) {
|
|
2991
|
+
const stateKey = `${familyKey}(${json.stringifyJson(moleculeKey)})`;
|
|
2992
|
+
(_d = tl.subscriptions.get(stateKey)) == null ? void 0 : _d();
|
|
2993
|
+
tl.subscriptions.delete(stateKey);
|
|
2994
|
+
store.timelineTopics.delete(stateKey);
|
|
2995
|
+
}
|
|
2996
|
+
}
|
|
2997
|
+
break;
|
|
2998
|
+
}
|
|
2999
|
+
})
|
|
3000
|
+
);
|
|
3001
|
+
}
|
|
3002
|
+
}
|
|
3003
|
+
function joinTransaction(tl, txUpdateInProgress, store) {
|
|
3004
|
+
const currentTxKey = txUpdateInProgress.key;
|
|
3005
|
+
const currentTxInstanceId = txUpdateInProgress.id;
|
|
3006
|
+
const currentTxToken = {
|
|
3007
|
+
key: currentTxKey,
|
|
3008
|
+
type: `transaction`
|
|
3009
|
+
};
|
|
3010
|
+
const currentTransaction = withdraw(currentTxToken, store);
|
|
3011
|
+
if (currentTxKey && tl.transactionKey === null) {
|
|
3012
|
+
tl.transactionKey = currentTxKey;
|
|
3013
|
+
const unsubscribe = currentTransaction.subject.subscribe(
|
|
3014
|
+
`timeline:${tl.key}`,
|
|
3015
|
+
(transactionUpdate) => {
|
|
3016
|
+
var _a, _b;
|
|
3017
|
+
unsubscribe();
|
|
3018
|
+
tl.transactionKey = null;
|
|
3019
|
+
if (tl.timeTraveling === null && currentTxInstanceId) {
|
|
3020
|
+
if (tl.at !== tl.history.length) {
|
|
3021
|
+
tl.history.splice(tl.at);
|
|
2943
3022
|
}
|
|
2944
|
-
const
|
|
2945
|
-
|
|
2946
|
-
|
|
2947
|
-
|
|
2948
|
-
|
|
2949
|
-
|
|
2950
|
-
|
|
2951
|
-
|
|
2952
|
-
|
|
3023
|
+
const timelineTopics = store.timelineTopics.getRelatedKeys(tl.key);
|
|
3024
|
+
const updates = filterTransactionUpdates(
|
|
3025
|
+
transactionUpdate.updates,
|
|
3026
|
+
timelineTopics
|
|
3027
|
+
);
|
|
3028
|
+
const timelineTransactionUpdate = __spreadProps(__spreadValues({
|
|
3029
|
+
timestamp: Date.now()
|
|
3030
|
+
}, transactionUpdate), {
|
|
3031
|
+
updates
|
|
3032
|
+
});
|
|
3033
|
+
const willCapture = (_b = (_a = tl.shouldCapture) == null ? void 0 : _a.call(tl, timelineTransactionUpdate, tl)) != null ? _b : true;
|
|
3034
|
+
if (willCapture) {
|
|
3035
|
+
tl.history.push(timelineTransactionUpdate);
|
|
3036
|
+
tl.at = tl.history.length;
|
|
3037
|
+
tl.subject.next(timelineTransactionUpdate);
|
|
2953
3038
|
}
|
|
2954
|
-
addAtomToTimeline(atom, tl, store);
|
|
2955
3039
|
}
|
|
3040
|
+
}
|
|
3041
|
+
);
|
|
3042
|
+
}
|
|
3043
|
+
}
|
|
3044
|
+
function filterTransactionUpdates(updates, timelineTopics) {
|
|
3045
|
+
return updates.filter((updateFromTx) => {
|
|
3046
|
+
if (updateFromTx.type === `transaction_update`) {
|
|
3047
|
+
return true;
|
|
3048
|
+
}
|
|
3049
|
+
let key;
|
|
3050
|
+
switch (updateFromTx.type) {
|
|
3051
|
+
case `state_creation`:
|
|
3052
|
+
case `state_disposal`:
|
|
3053
|
+
case `molecule_creation`:
|
|
3054
|
+
case `molecule_disposal`:
|
|
3055
|
+
key = updateFromTx.token.key;
|
|
2956
3056
|
break;
|
|
2957
|
-
|
|
2958
|
-
|
|
2959
|
-
const family = store.moleculeFamilies.get(tokenOrFamily.key);
|
|
2960
|
-
if (family) {
|
|
2961
|
-
tl.subscriptions.set(
|
|
2962
|
-
tokenOrFamily.key,
|
|
2963
|
-
family.subject.subscribe(
|
|
2964
|
-
`timeline:${options.key}`,
|
|
2965
|
-
(creationOrDisposal) => {
|
|
2966
|
-
var _a2, _b2;
|
|
2967
|
-
switch (creationOrDisposal.type) {
|
|
2968
|
-
case `molecule_creation`:
|
|
2969
|
-
{
|
|
2970
|
-
const molecule = store.molecules.get(
|
|
2971
|
-
json.stringifyJson(creationOrDisposal.token.key)
|
|
2972
|
-
);
|
|
2973
|
-
if (molecule) {
|
|
2974
|
-
const event = Object.assign(creationOrDisposal, {
|
|
2975
|
-
timestamp: Date.now()
|
|
2976
|
-
});
|
|
2977
|
-
tl.history.push(event);
|
|
2978
|
-
tl.at = tl.history.length;
|
|
2979
|
-
tl.subject.next(event);
|
|
2980
|
-
for (const token2 of molecule.tokens.values()) {
|
|
2981
|
-
switch (token2.type) {
|
|
2982
|
-
case `atom`:
|
|
2983
|
-
case `mutable_atom`:
|
|
2984
|
-
addAtomToTimeline(token2, tl, store);
|
|
2985
|
-
break;
|
|
2986
|
-
}
|
|
2987
|
-
}
|
|
2988
|
-
tl.subscriptions.set(
|
|
2989
|
-
molecule.key,
|
|
2990
|
-
molecule.subject.subscribe(
|
|
2991
|
-
`timeline:${options.key}`,
|
|
2992
|
-
(stateCreationOrDisposal) => {
|
|
2993
|
-
handleStateLifecycleEvent(
|
|
2994
|
-
stateCreationOrDisposal,
|
|
2995
|
-
tl,
|
|
2996
|
-
store
|
|
2997
|
-
);
|
|
2998
|
-
}
|
|
2999
|
-
)
|
|
3000
|
-
);
|
|
3001
|
-
}
|
|
3002
|
-
}
|
|
3003
|
-
break;
|
|
3004
|
-
case `molecule_disposal`:
|
|
3005
|
-
(_a2 = tl.subscriptions.get(creationOrDisposal.token.key)) == null ? void 0 : _a2();
|
|
3006
|
-
tl.subscriptions.delete(creationOrDisposal.token.key);
|
|
3007
|
-
for (const familyKey of creationOrDisposal.familyKeys) {
|
|
3008
|
-
const stateKey = `${familyKey}(${json.stringifyJson(
|
|
3009
|
-
creationOrDisposal.token.key
|
|
3010
|
-
)})`;
|
|
3011
|
-
(_b2 = tl.subscriptions.get(stateKey)) == null ? void 0 : _b2();
|
|
3012
|
-
tl.subscriptions.delete(stateKey);
|
|
3013
|
-
}
|
|
3014
|
-
break;
|
|
3015
|
-
}
|
|
3016
|
-
}
|
|
3017
|
-
)
|
|
3018
|
-
);
|
|
3019
|
-
}
|
|
3020
|
-
}
|
|
3057
|
+
default:
|
|
3058
|
+
key = updateFromTx.key;
|
|
3021
3059
|
break;
|
|
3022
3060
|
}
|
|
3023
|
-
|
|
3024
|
-
|
|
3025
|
-
|
|
3026
|
-
|
|
3027
|
-
|
|
3028
|
-
|
|
3029
|
-
|
|
3030
|
-
|
|
3061
|
+
return timelineTopics.has(key);
|
|
3062
|
+
}).map((updateFromTx) => {
|
|
3063
|
+
if (`updates` in updateFromTx) {
|
|
3064
|
+
return __spreadProps(__spreadValues({}, updateFromTx), {
|
|
3065
|
+
updates: filterTransactionUpdates(
|
|
3066
|
+
updateFromTx.updates,
|
|
3067
|
+
timelineTopics
|
|
3068
|
+
)
|
|
3069
|
+
});
|
|
3070
|
+
}
|
|
3071
|
+
return updateFromTx;
|
|
3072
|
+
});
|
|
3031
3073
|
}
|
|
3032
3074
|
function handleStateLifecycleEvent(event, tl, store) {
|
|
3033
|
-
var _a;
|
|
3075
|
+
var _a, _b;
|
|
3034
3076
|
const timestamp = Date.now();
|
|
3035
3077
|
const timelineEvent = Object.assign(event, {
|
|
3036
3078
|
timestamp
|
|
3037
3079
|
});
|
|
3038
3080
|
if (!tl.timeTraveling) {
|
|
3039
|
-
|
|
3040
|
-
|
|
3041
|
-
|
|
3081
|
+
const txUpdateInProgress = (_a = newest(store).on.transactionApplying.state) == null ? void 0 : _a.update;
|
|
3082
|
+
if (txUpdateInProgress) {
|
|
3083
|
+
joinTransaction(tl, txUpdateInProgress, store);
|
|
3084
|
+
} else {
|
|
3085
|
+
tl.history.push(timelineEvent);
|
|
3086
|
+
tl.at = tl.history.length;
|
|
3087
|
+
tl.subject.next(timelineEvent);
|
|
3088
|
+
}
|
|
3042
3089
|
}
|
|
3043
3090
|
switch (event.type) {
|
|
3044
3091
|
case `state_creation`:
|
|
3045
3092
|
addAtomToTimeline(event.token, tl, store);
|
|
3046
3093
|
break;
|
|
3047
3094
|
case `state_disposal`:
|
|
3048
|
-
(
|
|
3095
|
+
(_b = tl.subscriptions.get(event.token.key)) == null ? void 0 : _b();
|
|
3049
3096
|
tl.subscriptions.delete(event.token.key);
|
|
3050
3097
|
break;
|
|
3051
3098
|
}
|
|
@@ -3140,7 +3187,6 @@ exports.TRANSACTION_PHASES = TRANSACTION_PHASES;
|
|
|
3140
3187
|
exports.Tracker = Tracker;
|
|
3141
3188
|
exports.abortTransaction = abortTransaction;
|
|
3142
3189
|
exports.actUponStore = actUponStore;
|
|
3143
|
-
exports.addAtomToTimeline = addAtomToTimeline;
|
|
3144
3190
|
exports.applyTransaction = applyTransaction;
|
|
3145
3191
|
exports.arbitrary = arbitrary;
|
|
3146
3192
|
exports.assignTransactionToContinuity = assignTransactionToContinuity;
|