@typeonce/effect-machine 0.20.0 → 0.22.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +115 -5
- package/dist/Machine.d.ts +188 -52
- package/dist/Machine.d.ts.map +1 -1
- package/dist/Machine.js +6 -5
- package/dist/Machine.js.map +1 -1
- package/dist/internal/machine/executionPlan.d.ts.map +1 -1
- package/dist/internal/machine/executionPlan.js +50 -6
- package/dist/internal/machine/executionPlan.js.map +1 -1
- package/dist/internal/machine/initialization.d.ts.map +1 -1
- package/dist/internal/machine/initialization.js +7 -2
- package/dist/internal/machine/initialization.js.map +1 -1
- package/dist/internal/machine/machine.d.ts.map +1 -1
- package/dist/internal/machine/machine.js +132 -22
- package/dist/internal/machine/machine.js.map +1 -1
- package/dist/internal/machine/planner.d.ts +16 -2
- package/dist/internal/machine/planner.d.ts.map +1 -1
- package/dist/internal/machine/planner.js +67 -13
- package/dist/internal/machine/planner.js.map +1 -1
- package/dist/internal/machine/topology.d.ts +19 -2
- package/dist/internal/machine/topology.d.ts.map +1 -1
- package/dist/internal/machine/topology.js +17 -2
- package/dist/internal/machine/topology.js.map +1 -1
- package/dist/internal/testing/machine/finiteModel.d.ts.map +1 -1
- package/dist/internal/testing/machine/finiteModel.js +3 -3
- package/dist/internal/testing/machine/finiteModel.js.map +1 -1
- package/dist/internal/testing/machine/verification.d.ts.map +1 -1
- package/dist/internal/testing/machine/verification.js +17 -3
- package/dist/internal/testing/machine/verification.js.map +1 -1
- package/dist/testing/MachineTest.d.ts +5 -3
- package/dist/testing/MachineTest.d.ts.map +1 -1
- package/dist/testing/MachineTest.js +3 -3
- package/dist/testing/MachineTest.js.map +1 -1
- package/dist/unstable/reactivity/AtomMachine.d.ts +1 -1
- package/dist/unstable/reactivity/AtomMachine.js +1 -1
- package/docs/agent-guide.md +51 -3
- package/package.json +1 -1
- package/src/Machine.ts +532 -107
- package/src/internal/machine/executionPlan.ts +62 -6
- package/src/internal/machine/initialization.ts +10 -2
- package/src/internal/machine/machine.ts +188 -24
- package/src/internal/machine/planner.ts +86 -15
- package/src/internal/machine/topology.ts +40 -3
- package/src/internal/testing/machine/finiteModel.ts +7 -3
- package/src/internal/testing/machine/verification.ts +24 -3
- package/src/testing/MachineTest.ts +5 -3
- package/src/unstable/reactivity/AtomMachine.ts +1 -1
package/README.md
CHANGED
|
@@ -149,16 +149,26 @@ parallel root.
|
|
|
149
149
|
|
|
150
150
|
### Construct state through builders
|
|
151
151
|
|
|
152
|
-
Use `.from(...)` when constructing a new state from
|
|
152
|
+
Use `.from(...)` when constructing a new state from schema make input:
|
|
153
153
|
|
|
154
154
|
```ts
|
|
155
155
|
target.from({ draft: event.draft })
|
|
156
156
|
```
|
|
157
157
|
|
|
158
158
|
The machine runs these inputs through the state schema while planning. Schema
|
|
159
|
-
defaults, refinements, and tagged-class identity are
|
|
160
|
-
decode failures remain typed machine failures.
|
|
161
|
-
|
|
159
|
+
defaults, transformations, refinements, and tagged-class identity are
|
|
160
|
+
therefore preserved, and decode failures remain typed machine failures. This
|
|
161
|
+
is the default construction path.
|
|
162
|
+
|
|
163
|
+
Use `.decoded(...)` when the value is already a `Schema.Type`:
|
|
164
|
+
|
|
165
|
+
```ts
|
|
166
|
+
target.decoded(new Ready({ notice: null }))
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
The machine still validates the value against the schema's type side. It does
|
|
170
|
+
not run encoded-input transformations again. State builders are not callable;
|
|
171
|
+
the method name always makes the construction mode visible.
|
|
162
172
|
|
|
163
173
|
When sibling states share fields, remove the source discriminator and pass the
|
|
164
174
|
remaining fields through the target schema:
|
|
@@ -190,7 +200,7 @@ const States = Machine.states({
|
|
|
190
200
|
const definition = Machine.make({
|
|
191
201
|
states: States.states,
|
|
192
202
|
events: Machine.events(),
|
|
193
|
-
initial: (to) => to.Form.initial.resolve(({ target }) => target((form) => form.Editing.from()))
|
|
203
|
+
initial: (to) => to.Form.initial.resolve(({ target }) => target.from((form) => form.Editing.from()))
|
|
194
204
|
})
|
|
195
205
|
```
|
|
196
206
|
|
|
@@ -420,6 +430,106 @@ choice destinations remain calls such as `to.full.Running()`. Runtime named
|
|
|
420
430
|
branch builders remain callable, including `select.unchanged()`, because their
|
|
421
431
|
result carries the selected branch evidence.
|
|
422
432
|
|
|
433
|
+
### Update an active scope value
|
|
434
|
+
|
|
435
|
+
Use `to.local.update(...)` to replace the value owned by the nearest active
|
|
436
|
+
compound scope without rebuilding its active child. Use
|
|
437
|
+
`to.branch.<path>.update(...)` for a valued compound or parallel ancestor of the
|
|
438
|
+
handler source:
|
|
439
|
+
|
|
440
|
+
```ts
|
|
441
|
+
const handlers = {
|
|
442
|
+
Increment: (to) => to.branch.root.session.update(({ current, owner }) => owner.from({ count: current.count + 1 }))
|
|
443
|
+
}
|
|
444
|
+
```
|
|
445
|
+
|
|
446
|
+
The update keeps the exact active descendants, their values, history records,
|
|
447
|
+
completion outputs, and unrelated parallel regions. It runs no exit or entry
|
|
448
|
+
actions and does not restart state-owned work. Eventless stabilization still
|
|
449
|
+
runs, so an `always` transition can react to the new value.
|
|
450
|
+
|
|
451
|
+
The plain update method remains useful when topology does not change. It is
|
|
452
|
+
also a static selection for a named branch:
|
|
453
|
+
|
|
454
|
+
```ts
|
|
455
|
+
to.branches({
|
|
456
|
+
changed: { target: to.local.update },
|
|
457
|
+
unchanged: { target: to.none }
|
|
458
|
+
}).resolve(({ select, event }) =>
|
|
459
|
+
event.changed
|
|
460
|
+
? select.changed.from({ count: event.count })
|
|
461
|
+
: select.unchanged()
|
|
462
|
+
)
|
|
463
|
+
```
|
|
464
|
+
|
|
465
|
+
### Change topology and a retained owner together
|
|
466
|
+
|
|
467
|
+
When a transition enters another child and also replaces a valued ancestor
|
|
468
|
+
that stays active, declare both operations on the same target:
|
|
469
|
+
|
|
470
|
+
```ts
|
|
471
|
+
const handlers = {
|
|
472
|
+
CreatePlan: (to) =>
|
|
473
|
+
to.local.SavingPlan()
|
|
474
|
+
.updating(to.branch.Ready)
|
|
475
|
+
.resolve(({ current, event, owner, target }) =>
|
|
476
|
+
target.from({
|
|
477
|
+
request: { _tag: "Create", input: event.input }
|
|
478
|
+
}).update(
|
|
479
|
+
owner.decoded(new Ready({ ...current, notice: null }))
|
|
480
|
+
)
|
|
481
|
+
)
|
|
482
|
+
}
|
|
483
|
+
```
|
|
484
|
+
|
|
485
|
+
`to.local.SavingPlan()` selects topology. `.updating(to.branch.Ready)` names
|
|
486
|
+
the retained valued owner and makes its replacement mandatory: the resolver
|
|
487
|
+
does not type-check unless destination construction finishes with
|
|
488
|
+
`.update(...)`. `current` is that owner's decoded value from the
|
|
489
|
+
pre-transition snapshot. `target` constructs the destination; `owner`
|
|
490
|
+
constructs the complete replacement owner value.
|
|
491
|
+
|
|
492
|
+
The topology change and owner replacement apply atomically in one microstep.
|
|
493
|
+
The owner does not exit or reenter, its work is not restarted, and destination
|
|
494
|
+
entry actions observe the new owner value. Eventless stabilization follows.
|
|
495
|
+
Only one retained owner may be replaced by a combined target. A `full` target,
|
|
496
|
+
or any target that exits the selected owner, does not expose `.updating`.
|
|
497
|
+
Combined updates use a direct resolver in this release; named branches continue
|
|
498
|
+
to support value-only updates.
|
|
499
|
+
|
|
500
|
+
For a schema-less destination, construction remains explicit:
|
|
501
|
+
|
|
502
|
+
```ts
|
|
503
|
+
to.local.Idle()
|
|
504
|
+
.updating(to.branch.Ready)
|
|
505
|
+
.resolve(({ current, output, owner, target }) =>
|
|
506
|
+
target.from().update(
|
|
507
|
+
owner.decoded(
|
|
508
|
+
new Ready({
|
|
509
|
+
...current,
|
|
510
|
+
day: output,
|
|
511
|
+
notice: "Plan changed."
|
|
512
|
+
})
|
|
513
|
+
)
|
|
514
|
+
)
|
|
515
|
+
)
|
|
516
|
+
```
|
|
517
|
+
|
|
518
|
+
Both values derive from the same pre-transition snapshot and are validated
|
|
519
|
+
before lifecycle actions run. Competing transitions that write the same owner
|
|
520
|
+
conflict; document order and hierarchy select one writer rather than applying
|
|
521
|
+
last-write-wins behavior.
|
|
522
|
+
|
|
523
|
+
The resolver must return `target.decoded(value)` or `target.from(input)`. It
|
|
524
|
+
may return `decline()` only with `{ declinable: true }`. Pass `{ reenter: true }`
|
|
525
|
+
on event or invocation transitions when the handler source should exit and
|
|
526
|
+
enter again. Reentry applies to that source, not to the ancestor whose value
|
|
527
|
+
changed.
|
|
528
|
+
|
|
529
|
+
The selector omits `update` for schema-less scopes, atomic and final states,
|
|
530
|
+
inactive branches, parallel sibling regions, and choice resolvers. Updating a
|
|
531
|
+
parallel sibling requires an event handled by that region.
|
|
532
|
+
|
|
423
533
|
Use `declinable: true` when a resolver may decide that its transition is not
|
|
424
534
|
enabled. Only that resolver receives `decline()`, and its return type expands to
|
|
425
535
|
accept the opaque declined result:
|
package/dist/Machine.d.ts
CHANGED
|
@@ -191,7 +191,7 @@ export interface Definition<States extends Machine.StateSchemas, Events extends
|
|
|
191
191
|
* on: {
|
|
192
192
|
* Increment: (to) =>
|
|
193
193
|
* to.full.Count().resolve(({ event, state, target }) =>
|
|
194
|
-
* target(new Count({ value: state.value + event.by })))
|
|
194
|
+
* target.decoded(new Count({ value: state.value + event.by })))
|
|
195
195
|
* }
|
|
196
196
|
* }
|
|
197
197
|
* })
|
|
@@ -616,6 +616,15 @@ type FromMethod<Arguments extends ReadonlyArray<unknown>, Result> = {
|
|
|
616
616
|
*/
|
|
617
617
|
readonly from: FromCallable<Arguments, Machine.StateConstruction<Result>>;
|
|
618
618
|
};
|
|
619
|
+
type DecodedMethod<Arguments extends ReadonlyArray<unknown>, Result> = {
|
|
620
|
+
/**
|
|
621
|
+
* Constructs the selected state from an already-decoded schema value. The
|
|
622
|
+
* machine validates the value against the schema's type side while planning.
|
|
623
|
+
*
|
|
624
|
+
* @since 0.22.0
|
|
625
|
+
*/
|
|
626
|
+
readonly decoded: (...args: Arguments) => Result;
|
|
627
|
+
};
|
|
619
628
|
type ConstructionResult<Result> = Result | Machine.StateConstruction<Result>;
|
|
620
629
|
type UnwrapConstruction<Result> = Result extends Machine.StateConstruction<infer Value> ? Value : Result;
|
|
621
630
|
type NodeValue<Node> = [Machine.NodeSchema<Node>] extends [never] ? undefined : Machine.NodeSchema<Node>["Type"];
|
|
@@ -624,14 +633,14 @@ type WithNodeValue<Node, Rest extends ReadonlyArray<unknown>> = Machine.NodeSche
|
|
|
624
633
|
type WithNodeInput<Node, Rest extends ReadonlyArray<unknown>> = Machine.NodeSchema<Node> extends never ? Rest : readonly [input: NodeMakeInput<Node>, ...Rest];
|
|
625
634
|
type NodeBuilderMethod<Node, Arguments extends ReadonlyArray<unknown>, Result, FromArguments extends ReadonlyArray<unknown>, FromResult> = Machine.NodeSchema<Node> extends never ? {
|
|
626
635
|
readonly from: FromCallable<FromArguments, FromResult>;
|
|
627
|
-
} :
|
|
636
|
+
} : DecodedMethod<Arguments, Result> & {
|
|
628
637
|
readonly from: FromCallable<FromArguments, FromResult>;
|
|
629
638
|
};
|
|
630
|
-
type NodeMethod<Node, Arguments extends ReadonlyArray<unknown>, Result, FromArguments extends ReadonlyArray<unknown>> = Machine.NodeSchema<Node> extends never ? FromMethod<FromArguments, Result> :
|
|
639
|
+
type NodeMethod<Node, Arguments extends ReadonlyArray<unknown>, Result, FromArguments extends ReadonlyArray<unknown>> = Machine.NodeSchema<Node> extends never ? FromMethod<FromArguments, Result> : DecodedMethod<Arguments, Result> & FromMethod<FromArguments, Result>;
|
|
631
640
|
type NodeMethodWithInitial<Node, Arguments extends ReadonlyArray<unknown>, Result, FromArguments extends ReadonlyArray<unknown>, Path extends string> = Machine.NodeSchema<Node> extends never ? {
|
|
632
641
|
readonly from: FromCallable<FromArguments, Machine.StateConstruction<Result>>;
|
|
633
642
|
readonly initial: InitialTargetFactory<Node, Path>;
|
|
634
|
-
} :
|
|
643
|
+
} : DecodedMethod<Arguments, Result> & {
|
|
635
644
|
readonly from: FromCallable<FromArguments, Machine.StateConstruction<Result>>;
|
|
636
645
|
readonly initial: InitialTargetFactory<Node, Path>;
|
|
637
646
|
};
|
|
@@ -640,8 +649,8 @@ interface InitialTargetMethod<Node, Path extends string> {
|
|
|
640
649
|
readonly initial: InitialTargetFactory<Node, Path>;
|
|
641
650
|
}
|
|
642
651
|
interface InitialTargetFactory<Node, Path extends string> {
|
|
643
|
-
(...args: WithNodeValue<Node, readonly []>): Machine.InitialTarget<Path>;
|
|
644
652
|
readonly from: FromCallable<WithNodeInput<Node, readonly []>, Machine.StateConstruction<Machine.InitialTarget<Path>>>;
|
|
653
|
+
readonly decoded: (...args: WithNodeValue<Node, readonly []>) => Machine.InitialTarget<Path>;
|
|
645
654
|
}
|
|
646
655
|
type NodeConstructionSelectorFromCallable<Node, Builder, Result> = Machine.NodeSchema<Node> extends never ? {
|
|
647
656
|
<Selected extends ConstructionResult<Result>>(state: (builder: Builder) => Selected): Machine.StateConstruction<UnwrapConstruction<Selected>>;
|
|
@@ -649,7 +658,8 @@ type NodeConstructionSelectorFromCallable<Node, Builder, Result> = Machine.NodeS
|
|
|
649
658
|
type NestedTargetMethod<Node, Builder, Result, Path extends string> = Machine.NodeSchema<Node> extends never ? {
|
|
650
659
|
readonly from: NodeConstructionSelectorFromCallable<Node, Builder, Result>;
|
|
651
660
|
readonly initial: InitialTargetFactory<Node, Path>;
|
|
652
|
-
} :
|
|
661
|
+
} : {
|
|
662
|
+
readonly decoded: <Selected extends ConstructionResult<Result>>(value: NodeValue<Node>, state: (builder: Builder) => Selected) => Selected;
|
|
653
663
|
readonly from: NodeConstructionSelectorFromCallable<Node, Builder, Result>;
|
|
654
664
|
readonly initial: InitialTargetFactory<Node, Path>;
|
|
655
665
|
};
|
|
@@ -662,7 +672,7 @@ type InitialSnapshotBuilderWithPrefix<States extends Machine.StateSchemas, Prefi
|
|
|
662
672
|
} & {
|
|
663
673
|
readonly [Key in ChoiceStateKey<States>]: () => Machine.ChoiceTargetInstruction<Machine.JoinPath<Prefix, Key>>;
|
|
664
674
|
};
|
|
665
|
-
type InitialSnapshotMethod<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string> = Machine.NodeSchema<States[StateId]> extends never ? FromMethod<InitialSnapshotFromArguments<States, StateId, Prefix>, InitialSnapshotResult<States, StateId, Prefix>> :
|
|
675
|
+
type InitialSnapshotMethod<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string> = Machine.NodeSchema<States[StateId]> extends never ? FromMethod<InitialSnapshotFromArguments<States, StateId, Prefix>, InitialSnapshotResult<States, StateId, Prefix>> : DecodedMethod<InitialSnapshotArguments<States, StateId, Prefix>, InitialSnapshotResult<States, StateId, Prefix>> & FromMethod<InitialSnapshotFromArguments<States, StateId, Prefix>, InitialSnapshotResult<States, StateId, Prefix>>;
|
|
666
676
|
type InitialSnapshotArguments<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string, Path extends string = Machine.JoinPath<Prefix, StateId>> = States[StateId] extends infer Node ? Node extends {
|
|
667
677
|
readonly type: "parallel";
|
|
668
678
|
readonly states: infer Children extends Machine.StateSchemas;
|
|
@@ -711,7 +721,7 @@ type FullSnapshotBuilderWithPrefix<States extends Machine.StateSchemas, Prefix e
|
|
|
711
721
|
} & {
|
|
712
722
|
readonly [Key in ChoiceStateKey<States>]: () => Machine.ChoiceTargetInstruction<Machine.JoinPath<Prefix, Key>>;
|
|
713
723
|
};
|
|
714
|
-
type FullSnapshotMethod<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string> = Machine.NodeSchema<States[StateId]> extends never ? FromMethod<FullSnapshotFromArguments<States, StateId, Prefix>, FullSnapshotResult<States, StateId, Prefix>> :
|
|
724
|
+
type FullSnapshotMethod<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string> = Machine.NodeSchema<States[StateId]> extends never ? FromMethod<FullSnapshotFromArguments<States, StateId, Prefix>, FullSnapshotResult<States, StateId, Prefix>> : DecodedMethod<FullSnapshotArguments<States, StateId, Prefix>, FullSnapshotResult<States, StateId, Prefix>> & FromMethod<FullSnapshotFromArguments<States, StateId, Prefix>, FullSnapshotResult<States, StateId, Prefix>>;
|
|
715
725
|
type FullSnapshotArguments<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string, Path extends string = Machine.JoinPath<Prefix, StateId>> = States[StateId] extends infer Node ? Node extends {
|
|
716
726
|
readonly type: "parallel";
|
|
717
727
|
readonly states: infer Children extends Machine.StateSchemas;
|
|
@@ -774,7 +784,7 @@ type HistorySnapshotResult<States extends Machine.StateSchemas, StateId extends
|
|
|
774
784
|
} ? Machine.ParallelSnapshot<Path, NodeValue<Node>, HistorySnapshotRegions<Children, Path, Owner>> : Node extends {
|
|
775
785
|
readonly states: infer Children extends Machine.StateSchemas;
|
|
776
786
|
} ? Machine.CompoundSnapshot<Path, NodeValue<Node>, HistorySnapshotWithPrefix<Children, Owner, Path>> : never : never;
|
|
777
|
-
type HistorySnapshotMethod<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string, Owner extends string> = Machine.NodeSchema<States[StateId]> extends never ? FromMethod<HistorySnapshotFromArguments<States, StateId, Prefix, Owner>, HistorySnapshotResult<States, StateId, Prefix, Owner>> :
|
|
787
|
+
type HistorySnapshotMethod<States extends Machine.StateSchemas, StateId extends ActiveStateKey<States>, Prefix extends string, Owner extends string> = Machine.NodeSchema<States[StateId]> extends never ? FromMethod<HistorySnapshotFromArguments<States, StateId, Prefix, Owner>, HistorySnapshotResult<States, StateId, Prefix, Owner>> : DecodedMethod<HistorySnapshotArguments<States, StateId, Prefix, Owner>, HistorySnapshotResult<States, StateId, Prefix, Owner>> & FromMethod<HistorySnapshotFromArguments<States, StateId, Prefix, Owner>, HistorySnapshotResult<States, StateId, Prefix, Owner>>;
|
|
778
788
|
type HistorySnapshotWithPrefix<States extends Machine.StateSchemas, Owner extends string, Prefix extends string> = {
|
|
779
789
|
readonly [Key in ActiveStateKey<States>]: Owner extends Machine.JoinPath<Prefix, Key> | `${Machine.JoinPath<Prefix, Key>}.${string}` ? HistorySnapshotResult<States, Key, Prefix, Owner> : never;
|
|
780
790
|
}[ActiveStateKey<States>];
|
|
@@ -836,7 +846,8 @@ type LocalTargetBuilderForScope<States extends Machine.StateSchemas, Scope exten
|
|
|
836
846
|
*
|
|
837
847
|
* @since 0.4.0
|
|
838
848
|
*/
|
|
839
|
-
readonly with:
|
|
849
|
+
readonly with: {
|
|
850
|
+
readonly decoded: <Result extends ConstructionResult<LocalTargetResultWithPrefix<States, Children, Scope>>>(value: Machine.StateByIdentifier<States, Scope>, state: (builder: LocalTargetBuilderWithPrefix<States, Children, Scope, Source>) => Result) => Result;
|
|
840
851
|
readonly from: ConstructionSelectorFromCallable<Machine.SchemaByIdentifier<States, Scope>["~type.make.in"], LocalTargetBuilderWithPrefix<States, Children, Scope, Source>, LocalTargetResultWithPrefix<States, Children, Scope>>;
|
|
841
852
|
};
|
|
842
853
|
} : {}) : {};
|
|
@@ -2217,12 +2228,14 @@ export declare namespace Machine {
|
|
|
2217
2228
|
readonly type: "direct";
|
|
2218
2229
|
readonly target: Path | undefined;
|
|
2219
2230
|
readonly selection: TransitionTargetSelection<Path | undefined>;
|
|
2231
|
+
readonly updates: ReadonlyArray<string>;
|
|
2220
2232
|
} | {
|
|
2221
2233
|
readonly type: "branch";
|
|
2222
2234
|
readonly key: string;
|
|
2223
2235
|
readonly title: string;
|
|
2224
2236
|
readonly target: Path | undefined;
|
|
2225
2237
|
readonly selection: TransitionTargetSelection<Path | undefined>;
|
|
2238
|
+
readonly updates: ReadonlyArray<string>;
|
|
2226
2239
|
};
|
|
2227
2240
|
/** The statically selected root entry for machine startup. */
|
|
2228
2241
|
interface InitialDefinition<Path extends string = string> {
|
|
@@ -2234,9 +2247,10 @@ export declare namespace Machine {
|
|
|
2234
2247
|
*
|
|
2235
2248
|
* **Details**
|
|
2236
2249
|
*
|
|
2237
|
-
* Every branch exposes its
|
|
2238
|
-
* A compound local or branch target covers its descendants
|
|
2239
|
-
* `
|
|
2250
|
+
* Every branch exposes its static selection without executing its resolver.
|
|
2251
|
+
* A compound local or branch target covers its descendants. An `update`
|
|
2252
|
+
* selection keeps `target` undefined and records its value owner in
|
|
2253
|
+
* `selection.path`; `none` identifies an explicitly targetless branch.
|
|
2240
2254
|
*
|
|
2241
2255
|
* @category models
|
|
2242
2256
|
* @since 0.4.0
|
|
@@ -2281,6 +2295,8 @@ export declare namespace Machine {
|
|
|
2281
2295
|
* Choice microsteps retain each intermediate pseudo-state edge separately.
|
|
2282
2296
|
*/
|
|
2283
2297
|
readonly resolvedTarget: TargetPath | undefined;
|
|
2298
|
+
/** Retained valued owners replaced by this transition. */
|
|
2299
|
+
readonly updates: ReadonlyArray<string>;
|
|
2284
2300
|
}
|
|
2285
2301
|
/**
|
|
2286
2302
|
* Constructor arguments for a machine initial state function.
|
|
@@ -2841,6 +2857,38 @@ export declare namespace Machine {
|
|
|
2841
2857
|
readonly [AncestorStateId in ValuedStateIdentifier<States>]: StateByIdentifier<States, AncestorStateId>;
|
|
2842
2858
|
}>;
|
|
2843
2859
|
}
|
|
2860
|
+
/**
|
|
2861
|
+
* Opaque instruction that replaces one active compound or parallel state's
|
|
2862
|
+
* value without changing its active descendants.
|
|
2863
|
+
*
|
|
2864
|
+
* @category models
|
|
2865
|
+
* @since 0.21.0
|
|
2866
|
+
*/
|
|
2867
|
+
interface StateUpdate<States extends StateSchemas, StateId extends ValuedStateIdentifier<States>> {
|
|
2868
|
+
readonly [Topology.StateUpdateTypeId]: {
|
|
2869
|
+
readonly states: Types.Covariant<States>;
|
|
2870
|
+
readonly owner: Types.Covariant<StateId>;
|
|
2871
|
+
};
|
|
2872
|
+
}
|
|
2873
|
+
/**
|
|
2874
|
+
* Opaque result that combines one topology target with one retained owner
|
|
2875
|
+
* value replacement in the same microstep.
|
|
2876
|
+
*
|
|
2877
|
+
* @category models
|
|
2878
|
+
* @since 0.22.0
|
|
2879
|
+
*/
|
|
2880
|
+
interface CombinedTarget<Result, States extends StateSchemas, Owner extends ValuedStateIdentifier<States>> {
|
|
2881
|
+
readonly [Topology.CombinedTargetTypeId]: {
|
|
2882
|
+
readonly result: Types.Covariant<Result>;
|
|
2883
|
+
readonly states: Types.Covariant<States>;
|
|
2884
|
+
readonly owner: Types.Covariant<Owner>;
|
|
2885
|
+
};
|
|
2886
|
+
}
|
|
2887
|
+
/** @internal */
|
|
2888
|
+
type StateUpdateBuilder<States extends StateSchemas, StateId extends ValuedStateIdentifier<States>> = {
|
|
2889
|
+
readonly decoded: (value: StateByIdentifier<States, StateId>) => StateUpdate<States, StateId>;
|
|
2890
|
+
readonly from: FromCallable<readonly [input: SchemaByIdentifier<States, StateId>["~type.make.in"]], StateUpdate<States, StateId>>;
|
|
2891
|
+
};
|
|
2844
2892
|
/**
|
|
2845
2893
|
* Opaque result returned by an explicitly targetless transition.
|
|
2846
2894
|
*
|
|
@@ -3025,40 +3073,56 @@ export declare namespace Machine {
|
|
|
3025
3073
|
* @category models
|
|
3026
3074
|
* @since 0.14.0
|
|
3027
3075
|
*/
|
|
3028
|
-
interface TargetSelection<out Result, out Path extends string | undefined = string | undefined, out Kind extends Topology.TargetSelectionKind = Topology.TargetSelectionKind> {
|
|
3076
|
+
interface TargetSelection<out Result, out Path extends string | undefined = string | undefined, out Kind extends Topology.TargetSelectionKind = Topology.TargetSelectionKind, out Scope extends Topology.TargetSelectionScope | undefined = Topology.TargetSelectionScope | undefined> {
|
|
3029
3077
|
readonly [Topology.TargetSelectionTypeId]: typeof Topology.TargetSelectionTypeId;
|
|
3030
3078
|
readonly kind: Kind;
|
|
3031
|
-
readonly scope:
|
|
3079
|
+
readonly scope: Scope;
|
|
3032
3080
|
readonly path: Path;
|
|
3033
3081
|
readonly "~effect/Machine/TargetSelectionResult"?: Types.Covariant<Result>;
|
|
3034
3082
|
}
|
|
3035
|
-
type SelectionValue<Builder, Path extends string, Kind extends Topology.TargetSelectionKind = "state"> = TargetSelection<Builder, Path, Kind>;
|
|
3036
|
-
type SelectionMethod<Builder, Path extends string, Kind extends Topology.TargetSelectionKind = "state"> = () => SelectionValue<Builder, Path, Kind>;
|
|
3037
|
-
type InitialSelectionMethod<Builder, Path extends string> = Builder extends {
|
|
3083
|
+
type SelectionValue<Builder, Path extends string, Kind extends Topology.TargetSelectionKind = "state", Scope extends Topology.TargetSelectionScope | undefined = Topology.TargetSelectionScope | undefined> = TargetSelection<Builder, Path, Kind, Scope>;
|
|
3084
|
+
type SelectionMethod<Builder, Path extends string, Kind extends Topology.TargetSelectionKind = "state", Scope extends Topology.TargetSelectionScope | undefined = Topology.TargetSelectionScope | undefined> = () => SelectionValue<Builder, Path, Kind, Scope>;
|
|
3085
|
+
type InitialSelectionMethod<Builder, Path extends string, Scope extends Topology.TargetSelectionScope> = Builder extends {
|
|
3038
3086
|
readonly initial: infer Initial;
|
|
3039
3087
|
} ? {
|
|
3040
|
-
readonly initial: SelectionValue<Initial, Path, "initial">;
|
|
3088
|
+
readonly initial: SelectionValue<Initial, Path, "initial", Scope>;
|
|
3041
3089
|
} : {};
|
|
3042
3090
|
type SelectionTreeWithPrefix<AllStates extends StateSchemas, States extends StateSchemas, Prefix extends string, Scope extends "local" | "branch", Builder> = {
|
|
3043
3091
|
readonly [Key in Extract<ActiveStateKey<States> | ChoiceStateKey<States>, keyof Builder>]: SelectionNode<AllStates, States[Key], JoinPath<Prefix, Key>, Scope, Builder[Key]>;
|
|
3044
3092
|
};
|
|
3045
|
-
type SelectionNode<AllStates extends StateSchemas, Node, Path extends string, Scope extends "local" | "branch", Builder> = Node extends ChoiceStateNodeConfig ? SelectionMethod<Builder, Path, "choice"> : Node extends {
|
|
3093
|
+
type SelectionNode<AllStates extends StateSchemas, Node, Path extends string, Scope extends "local" | "branch", Builder> = Node extends ChoiceStateNodeConfig ? SelectionMethod<Builder, Path, "choice", Scope> : Node extends {
|
|
3046
3094
|
readonly states: infer Children extends StateSchemas;
|
|
3047
|
-
} ? SelectionMethod<Builder, Path> & InitialSelectionMethod<Builder, Path> & SelectionTreeWithPrefix<AllStates, Children, Path, Scope, Builder> : SelectionMethod<Builder, Path>;
|
|
3095
|
+
} ? SelectionMethod<Builder, Path, "state", Scope> & InitialSelectionMethod<Builder, Path, Scope> & SelectionTreeWithPrefix<AllStates, Children, Path, Scope, Builder> : SelectionMethod<Builder, Path, "state", Scope>;
|
|
3096
|
+
/** @internal */
|
|
3097
|
+
type StateUpdateSelectionForNode<AllStates extends StateSchemas, Node, Path extends string, Scope extends "local" | "branch"> = Node extends {
|
|
3098
|
+
readonly states: StateSchemas;
|
|
3099
|
+
} ? NodeSchema<Node> extends never ? {} : {
|
|
3100
|
+
readonly update: SelectionValue<StateUpdateBuilder<AllStates, Extract<Path, ValuedStateIdentifier<AllStates>>>, Path, "update", Scope>;
|
|
3101
|
+
} : {};
|
|
3102
|
+
/** @internal */
|
|
3103
|
+
type BranchUpdateSelectionPath<AllStates extends StateSchemas, Node, Path extends string, Rest extends string, Scope extends "local" | "branch" = "branch"> = StateUpdateSelectionForNode<AllStates, Node, Path, Scope> & (Node extends {
|
|
3104
|
+
readonly states: infer Children extends StateSchemas;
|
|
3105
|
+
} ? Rest extends `${infer Head}.${infer Tail}` ? Head extends keyof Children ? {
|
|
3106
|
+
readonly [Key in Head]: BranchUpdateSelectionPath<AllStates, Children[Head], JoinPath<Path, Head>, Tail, Scope>;
|
|
3107
|
+
} : {} : Rest extends keyof Children ? {
|
|
3108
|
+
readonly [Key in Rest]: StateUpdateSelectionForNode<AllStates, Children[Rest], JoinPath<Path, Rest>, Scope>;
|
|
3109
|
+
} : {} : {});
|
|
3048
3110
|
type FullSelectionNode<AllStates extends StateSchemas, Node, Path extends StateIdentifier<AllStates>, Builder> = Node extends {
|
|
3049
3111
|
readonly states: StateSchemas;
|
|
3050
|
-
} ? SelectionMethod<Builder, Path> & InitialSelectionMethod<Builder, Path> : SelectionMethod<Builder, Path>;
|
|
3112
|
+
} ? SelectionMethod<Builder, Path, "state", "full"> & InitialSelectionMethod<Builder, Path, "full"> : SelectionMethod<Builder, Path, "state", "full">;
|
|
3051
3113
|
type FullTargetSelector<States extends StateSchemas> = {
|
|
3052
3114
|
readonly [Key in Extract<ActiveStateKey<States>, keyof FullTargetBuilder<States>>]: FullSelectionNode<States, States[Key], Extract<Key, StateIdentifier<States>>, FullTargetBuilder<States>[Key]>;
|
|
3053
3115
|
};
|
|
3054
3116
|
type BranchTargetSelector<States extends StateSchemas, Source extends StateNodeIdentifier<States>, Root extends string = Source extends `${infer Head}.${string}` ? Head : Source> = Root extends ActiveStateKey<States> ? Root extends keyof BranchTargetBuilder<States, Source> ? {
|
|
3055
|
-
readonly [Key in Root]: SelectionNode<States, States[Key], Key, "branch", BranchTargetBuilder<States, Source>[Key]
|
|
3117
|
+
readonly [Key in Root]: SelectionNode<States, States[Key], Key, "branch", BranchTargetBuilder<States, Source>[Key]> & (Source extends ChoiceIdentifier<States> ? {} : Source extends `${Key}.${infer Rest}` ? BranchUpdateSelectionPath<States, States[Key], Key, Rest> : StateUpdateSelectionForNode<States, States[Key], Key, "branch">);
|
|
3056
3118
|
} : {} : {};
|
|
3057
|
-
type LocalTargetSelector<States extends StateSchemas, Source extends StateNodeIdentifier<States>> = NearestCompoundScope<States, Source> extends infer Scope extends StateIdentifier<States> ? ChildrenOf<States, Scope> extends infer Children extends StateSchemas ? LocalTargetBuilder<States, Source> extends infer Builder ? SelectionTreeWithPrefix<States, Children, Scope, "local", Builder> & ("with" extends keyof Builder ? {
|
|
3058
|
-
readonly with: SelectionValue<Builder["with"], Scope>;
|
|
3059
|
-
} : {})
|
|
3119
|
+
type LocalTargetSelector<States extends StateSchemas, Source extends StateNodeIdentifier<States>> = NearestCompoundScope<States, Source> extends infer Scope ? [Scope] extends [never] ? {} : Scope extends StateIdentifier<States> ? ChildrenOf<States, Scope> extends infer Children extends StateSchemas ? LocalTargetBuilder<States, Source> extends infer Builder ? SelectionTreeWithPrefix<States, Children, Scope, "local", Builder> & ("with" extends keyof Builder ? {
|
|
3120
|
+
readonly with: SelectionValue<Builder["with"], Scope, "state", "local">;
|
|
3121
|
+
} : {}) & (Source extends ChoiceIdentifier<States> ? {} : Scope extends ValuedStateIdentifier<States> ? {
|
|
3122
|
+
readonly update: SelectionValue<StateUpdateBuilder<States, Scope>, Scope, "update", "local">;
|
|
3123
|
+
} : {}) : {} : {} : {} : {};
|
|
3060
3124
|
type HistorySelectionTree<AllStates extends StateSchemas, States extends StateSchemas, Prefix extends string, Builder> = {
|
|
3061
|
-
readonly [Key in Extract<HistoryContainingKey<States>, keyof Builder>]: States[Key] extends HistoryStateNodeConfig ? SelectionValue<Builder[Key], JoinPath<Prefix, Key>, "history"> : States[Key] extends {
|
|
3125
|
+
readonly [Key in Extract<HistoryContainingKey<States>, keyof Builder>]: States[Key] extends HistoryStateNodeConfig ? SelectionValue<Builder[Key], JoinPath<Prefix, Key>, "history", "full"> : States[Key] extends {
|
|
3062
3126
|
readonly states: infer Children extends StateSchemas;
|
|
3063
3127
|
} ? HistorySelectionTree<AllStates, Children, JoinPath<Prefix, Key>, Builder[Key]> : never;
|
|
3064
3128
|
};
|
|
@@ -3073,10 +3137,10 @@ export declare namespace Machine {
|
|
|
3073
3137
|
*/
|
|
3074
3138
|
interface TargetSelector<States extends StateSchemas, Source extends StateNodeIdentifier<States>> {
|
|
3075
3139
|
/** Handles the trigger without selecting a destination. */
|
|
3076
|
-
readonly none: SelectionValue<TargetBuilder<States, Source>["none"], never, "none">;
|
|
3077
|
-
/** Selects a destination
|
|
3140
|
+
readonly none: SelectionValue<TargetBuilder<States, Source>["none"], never, "none", "local">;
|
|
3141
|
+
/** Selects a destination or updates the nearest active compound scope. */
|
|
3078
3142
|
readonly local: LocalTargetSelector<States, Source>;
|
|
3079
|
-
/** Selects a destination
|
|
3143
|
+
/** Selects a destination or updates a valued active ancestor under the current root. */
|
|
3080
3144
|
readonly branch: BranchTargetSelector<States, Source>;
|
|
3081
3145
|
/** Selects a complete destination under any top-level state. */
|
|
3082
3146
|
readonly full: FullTargetSelector<States>;
|
|
@@ -3088,8 +3152,8 @@ export declare namespace Machine {
|
|
|
3088
3152
|
readonly [Key in Extract<ActiveStateKey<States>, keyof InitialBuilder<States>>]: States[Key] extends {
|
|
3089
3153
|
readonly states: StateSchemas;
|
|
3090
3154
|
} ? {
|
|
3091
|
-
readonly initial: SelectionValue<InitialBuilder<States>[Key], Key, "initial">;
|
|
3092
|
-
} : SelectionMethod<InitialBuilder<States>[Key], Key>;
|
|
3155
|
+
readonly initial: SelectionValue<InitialBuilder<States>[Key], Key, "initial", "initial">;
|
|
3156
|
+
} : SelectionMethod<InitialBuilder<States>[Key], Key, "state", "initial">;
|
|
3093
3157
|
};
|
|
3094
3158
|
/**
|
|
3095
3159
|
* Context passed to a state/event handler.
|
|
@@ -3365,14 +3429,14 @@ export declare namespace Machine {
|
|
|
3365
3429
|
* **Details**
|
|
3366
3430
|
*
|
|
3367
3431
|
* Handlers return snapshots for complete state replacement, target builder
|
|
3368
|
-
* results for path-safe partial transitions,
|
|
3369
|
-
* explicitly targetless transition. Raw decoded state
|
|
3370
|
-
* not accepted at transition boundaries.
|
|
3432
|
+
* results for path-safe partial transitions, state-value updates, or
|
|
3433
|
+
* `target.none()` for an explicitly targetless transition. Raw decoded state
|
|
3434
|
+
* values and `void` are not accepted at transition boundaries.
|
|
3371
3435
|
*
|
|
3372
3436
|
* @category utility types
|
|
3373
3437
|
* @since 0.4.0
|
|
3374
3438
|
*/
|
|
3375
|
-
type HandlerResult<States extends StateSchemas, E, R> = Snapshot<States> | Target<States, StateIdentifier<States>> | HistoryTarget<States, HistoryIdentifier<States>> | ChoiceTarget<States, ChoiceIdentifier<States>> | StateConstruction<Snapshot<States> | Target<States, StateIdentifier<States>> | HistoryTarget<States, HistoryIdentifier<States>> | ChoiceTarget<States, ChoiceIdentifier<States>>> | NoTarget;
|
|
3439
|
+
type HandlerResult<States extends StateSchemas, E, R> = Snapshot<States> | Target<States, StateIdentifier<States>> | HistoryTarget<States, HistoryIdentifier<States>> | ChoiceTarget<States, ChoiceIdentifier<States>> | StateUpdate<States, ValuedStateIdentifier<States>> | CombinedTarget<Target<States, StateIdentifier<States>> | Snapshot<States>, States, ValuedStateIdentifier<States>> | StateConstruction<Snapshot<States> | Target<States, StateIdentifier<States>> | HistoryTarget<States, HistoryIdentifier<States>> | ChoiceTarget<States, ChoiceIdentifier<States>> | StateUpdate<States, ValuedStateIdentifier<States>>> | NoTarget;
|
|
3376
3440
|
/** A choice resolver must always select a typed target synchronously. */
|
|
3377
3441
|
type ChoiceResult<States extends StateSchemas, E, R> = Snapshot<States> | Target<States, StateIdentifier<States>> | HistoryTarget<States, HistoryIdentifier<States>> | ChoiceTarget<States, ChoiceIdentifier<States>> | StateConstruction<Snapshot<States> | Target<States, StateIdentifier<States>> | HistoryTarget<States, HistoryIdentifier<States>> | ChoiceTarget<States, ChoiceIdentifier<States>>>;
|
|
3378
3442
|
/**
|
|
@@ -3613,19 +3677,59 @@ export declare namespace Machine {
|
|
|
3613
3677
|
}
|
|
3614
3678
|
/** The only transition value accepted by machine handler APIs. */
|
|
3615
3679
|
type TransitionConfig<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean = false, Acceptance extends TransitionAcceptance = "required"> = TransitionBuilderInput<States, Events, Emits, StateId, Context, Reenter, Acceptance>;
|
|
3616
|
-
type SelectionBuilder<Selection> = Selection extends TargetSelection<infer Builder, any, any> ? Builder : never;
|
|
3617
|
-
type SelectionKind<Selection> = Selection extends TargetSelection<any, any, infer Kind> ? Kind : never;
|
|
3618
|
-
type SelectionPath<Selection> = Selection extends TargetSelection<any, infer Path, any> ? Path : never;
|
|
3680
|
+
type SelectionBuilder<Selection> = Selection extends TargetSelection<infer Builder, any, any, any> ? Builder : never;
|
|
3681
|
+
type SelectionKind<Selection> = Selection extends TargetSelection<any, any, infer Kind, any> ? Kind : never;
|
|
3682
|
+
type SelectionPath<Selection> = Selection extends TargetSelection<any, infer Path, any, any> ? Path : never;
|
|
3683
|
+
type SelectionScope<Selection> = Selection extends TargetSelection<any, any, any, infer Scope> ? Scope : never;
|
|
3619
3684
|
type TargetBuilderResult<Builder> = (Builder extends (...args: any) => infer Result ? Result : never) | (Builder extends {
|
|
3685
|
+
readonly decoded: (...args: any) => infer Result;
|
|
3686
|
+
} ? Result : never) | (Builder extends {
|
|
3620
3687
|
readonly from: (...args: any) => infer Result;
|
|
3621
3688
|
} ? Result : never);
|
|
3622
3689
|
type SelectedTargetResult<Selection> = SelectionBuilder<Selection> extends infer Builder ? TargetBuilderResult<Builder> : never;
|
|
3690
|
+
type RetainedUpdateOwner<States extends StateSchemas, Source extends StateNodeIdentifier<States>, Selection> = Extract<ParentStateIdentifier<Source>, ParentStateIdentifier<Extract<SelectionPath<Selection>, string>> & ValuedStateIdentifier<States>>;
|
|
3691
|
+
type RetainedOwnerSelector<Owner extends string> = () => TargetSelection<any, Owner, "state", "branch">;
|
|
3692
|
+
/**
|
|
3693
|
+
* Destination construction returned when a transition declares one retained
|
|
3694
|
+
* valued owner with `.updating(...)`.
|
|
3695
|
+
*
|
|
3696
|
+
* @category models
|
|
3697
|
+
* @since 0.22.0
|
|
3698
|
+
*/
|
|
3699
|
+
interface UpdatingStateConstruction<Result, States extends StateSchemas, Owner extends ValuedStateIdentifier<States>> {
|
|
3700
|
+
/** Combines the selected topology with the required owner replacement. */
|
|
3701
|
+
readonly update: (update: StateUpdate<States, Owner>) => CombinedTarget<UnwrapConstruction<Result>, States, Owner>;
|
|
3702
|
+
}
|
|
3703
|
+
type UpdatingCallable<Callable, States extends StateSchemas, Owner extends ValuedStateIdentifier<States>> = Callable extends {
|
|
3704
|
+
(...args: infer Arguments1): infer Result1;
|
|
3705
|
+
(...args: infer Arguments2): infer Result2;
|
|
3706
|
+
} ? {
|
|
3707
|
+
(...args: Arguments1): UpdatingStateConstruction<Result1, States, Owner>;
|
|
3708
|
+
(...args: Arguments2): UpdatingStateConstruction<Result2, States, Owner>;
|
|
3709
|
+
} : Callable extends (...args: infer Arguments) => infer Result ? (...args: Arguments) => UpdatingStateConstruction<Result, States, Owner> : never;
|
|
3710
|
+
type UpdatingTargetBuilder<Builder, States extends StateSchemas, Owner extends ValuedStateIdentifier<States>> = {
|
|
3711
|
+
readonly [Key in keyof Builder]: Key extends "from" | "decoded" ? UpdatingCallable<Builder[Key], States, Owner> : Builder[Key];
|
|
3712
|
+
};
|
|
3623
3713
|
type SelectionSupportsDefaultConstruction<Selection> = SelectionKind<Selection> extends "none" ? true : SelectionBuilder<Selection> extends {
|
|
3624
3714
|
readonly from: (...args: infer Args) => any;
|
|
3625
|
-
} ? [] extends Args ? true : false :
|
|
3715
|
+
} ? [] extends Args ? true : false : false;
|
|
3626
3716
|
type TransitionResolveContext<Context, Selection> = Omit<Context, "target"> & (SelectionKind<Selection> extends "none" ? {} : {
|
|
3627
3717
|
readonly target: SelectionBuilder<Selection>;
|
|
3628
3718
|
});
|
|
3719
|
+
type StateUpdateResolveContext<States extends StateSchemas, Context, Owner extends ValuedStateIdentifier<States>> = Omit<Context, "target"> & {
|
|
3720
|
+
/** Decoded owner value from the pre-transition snapshot. */
|
|
3721
|
+
readonly current: StateByIdentifier<States, Owner>;
|
|
3722
|
+
/** Constructs the complete replacement for the selected owner. */
|
|
3723
|
+
readonly owner: StateUpdateBuilder<States, Owner>;
|
|
3724
|
+
};
|
|
3725
|
+
type UpdatingTransitionResolveContext<States extends StateSchemas, Context, Selection, Owner extends ValuedStateIdentifier<States>> = Omit<Context, "target"> & {
|
|
3726
|
+
/** Decoded owner value from the pre-transition snapshot. */
|
|
3727
|
+
readonly current: StateByIdentifier<States, Owner>;
|
|
3728
|
+
/** Constructs the selected topology and requires `.update(...)`. */
|
|
3729
|
+
readonly target: UpdatingTargetBuilder<SelectionBuilder<Selection>, States, Owner>;
|
|
3730
|
+
/** Constructs the complete replacement for the retained owner. */
|
|
3731
|
+
readonly owner: StateUpdateBuilder<States, Owner>;
|
|
3732
|
+
};
|
|
3629
3733
|
/** Context capability available only to explicitly declinable resolvers. */
|
|
3630
3734
|
interface DeclineCapability {
|
|
3631
3735
|
/** Declines this candidate and continues hierarchical transition selection. */
|
|
@@ -3633,6 +3737,10 @@ export declare namespace Machine {
|
|
|
3633
3737
|
}
|
|
3634
3738
|
type TransitionResolver<Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, Context, Selection> = (context: TransitionResolveContext<Context, Selection>, enqueue: Enqueue<EventOf<Events>, EmitOf<Emits>>) => SelectionKind<Selection> extends "none" ? undefined : SelectedTargetResult<Selection> | undefined;
|
|
3635
3739
|
type DeclinableTransitionResolver<Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, Context, Selection> = (context: TransitionResolveContext<Context, Selection> & DeclineCapability, enqueue: Enqueue<EventOf<Events>, EmitOf<Emits>>) => (SelectionKind<Selection> extends "none" ? undefined : SelectedTargetResult<Selection> | undefined) | Declined;
|
|
3740
|
+
/** @internal */
|
|
3741
|
+
type StateUpdateResolver<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, Context, Owner extends ValuedStateIdentifier<States>> = (context: StateUpdateResolveContext<States, Context, Owner>, enqueue: Enqueue<EventOf<Events>, EmitOf<Emits>>) => StateUpdate<States, Owner>;
|
|
3742
|
+
/** @internal */
|
|
3743
|
+
type DeclinableStateUpdateResolver<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, Context, Owner extends ValuedStateIdentifier<States>> = (context: StateUpdateResolveContext<States, Context, Owner> & DeclineCapability, enqueue: Enqueue<EventOf<Events>, EmitOf<Emits>>) => StateUpdate<States, Owner> | Declined;
|
|
3636
3744
|
/** One named destination declared by a branching transition. */
|
|
3637
3745
|
interface TransitionBranchInput<Selection extends TargetSelection<any, any, any> = TargetSelection<any, any, any>> {
|
|
3638
3746
|
/** Exact topology destination available to the branching resolver. */
|
|
@@ -3716,15 +3824,33 @@ export declare namespace Machine {
|
|
|
3716
3824
|
* @inlineType TransitionReenterOption
|
|
3717
3825
|
*/
|
|
3718
3826
|
type TransitionTarget<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean, Acceptance extends TransitionAcceptance, Selection extends TargetSelection<any, any, any>> = Selection & (SelectionSupportsDefaultConstruction<Selection> extends true ? BuiltTransition<States, Events, Emits, StateId, Context, Reenter, SelectionKind<Selection> extends "none" ? undefined : SelectedTargetResult<Selection> | undefined, "required"> : {}) & {
|
|
3719
|
-
/**
|
|
3720
|
-
* Evaluates state construction and queued commands only after this
|
|
3721
|
-
* transition has been selected.
|
|
3722
|
-
*/
|
|
3827
|
+
/** Evaluates state construction after this transition is selected. */
|
|
3723
3828
|
readonly resolve: TransitionResolveRequired<States, Events, Emits, StateId, Context, Reenter, Selection> & ("declinable" extends Acceptance ? TransitionResolveDeclinable<States, Events, Emits, StateId, Context, Reenter, Selection> : {});
|
|
3724
3829
|
} & ([Reenter] extends [true] ? SelectionSupportsDefaultConstruction<Selection> extends true ? {
|
|
3725
3830
|
/** Reenters the source using the selected target's default construction. */
|
|
3726
3831
|
readonly reenter: () => BuiltTransition<States, Events, Emits, StateId, Context, Reenter, SelectionKind<Selection> extends "none" ? undefined : SelectedTargetResult<Selection> | undefined, "required">;
|
|
3727
|
-
} : {} : {})
|
|
3832
|
+
} : {} : {}) & (SelectionKind<Selection> extends "state" ? SelectionScope<Selection> extends "local" | "branch" ? RetainedUpdateOwner<States, StateId, Selection> extends infer Owner extends ValuedStateIdentifier<States> ? [
|
|
3833
|
+
Owner
|
|
3834
|
+
] extends [never] ? {} : {
|
|
3835
|
+
/** Declares one valued owner retained by the selected topology. */
|
|
3836
|
+
readonly updating: <SelectedOwner extends Owner>(owner: RetainedOwnerSelector<SelectedOwner>) => UpdatingTransitionTarget<States, Events, Emits, StateId, Context, Reenter, Acceptance, Selection, SelectedOwner>;
|
|
3837
|
+
} : {} : {} : {});
|
|
3838
|
+
/** A topology selection that requires one retained owner replacement. */
|
|
3839
|
+
type UpdatingTransitionTarget<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean, Acceptance extends TransitionAcceptance, Selection extends TargetSelection<any, any, "state">, Owner extends ValuedStateIdentifier<States>> = Selection & {
|
|
3840
|
+
/** @internal */
|
|
3841
|
+
readonly "~effect/Machine/UpdatingTransitionTarget": Owner;
|
|
3842
|
+
readonly resolve: ((resolve: (context: UpdatingTransitionResolveContext<States, Context, Selection, Owner>, enqueue: Enqueue<EventOf<Events>, EmitOf<Emits>>) => CombinedTarget<UnwrapConstruction<SelectedTargetResult<Selection>>, States, Owner>, options?: TransitionRequiredOptions<Reenter>) => BuiltTransition<States, Events, Emits, StateId, Context, Reenter, CombinedTarget<UnwrapConstruction<SelectedTargetResult<Selection>>, States, Owner>, "required">) & ("declinable" extends Acceptance ? (resolve: (context: UpdatingTransitionResolveContext<States, Context, Selection, Owner> & DeclineCapability, enqueue: Enqueue<EventOf<Events>, EmitOf<Emits>>) => CombinedTarget<UnwrapConstruction<SelectedTargetResult<Selection>>, States, Owner> | Declined, options: TransitionDeclinableOptions<Reenter>) => BuiltTransition<States, Events, Emits, StateId, Context, Reenter, CombinedTarget<UnwrapConstruction<SelectedTargetResult<Selection>>, States, Owner> | Declined, "declinable"> : {});
|
|
3843
|
+
};
|
|
3844
|
+
/** @internal */
|
|
3845
|
+
interface StateUpdateTransitionRequired<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean, Selection extends TargetSelection<any, any, "update">> {
|
|
3846
|
+
(resolve: StateUpdateResolver<States, Events, Emits, Context, Extract<SelectionPath<Selection>, ValuedStateIdentifier<States>>>, options?: TransitionRequiredOptions<Reenter>): BuiltTransition<States, Events, Emits, StateId, Context, Reenter, SelectedTargetResult<Selection>, "required">;
|
|
3847
|
+
}
|
|
3848
|
+
/** @internal */
|
|
3849
|
+
interface StateUpdateTransitionDeclinable<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean, Selection extends TargetSelection<any, any, "update">> {
|
|
3850
|
+
(resolve: DeclinableStateUpdateResolver<States, Events, Emits, Context, Extract<SelectionPath<Selection>, ValuedStateIdentifier<States>>>, options: TransitionDeclinableOptions<Reenter>): BuiltTransition<States, Events, Emits, StateId, Context, Reenter, SelectedTargetResult<Selection> | Declined, "declinable">;
|
|
3851
|
+
}
|
|
3852
|
+
/** @internal */
|
|
3853
|
+
type StateUpdateTransition<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean, Acceptance extends TransitionAcceptance, Selection extends TargetSelection<any, any, "update">> = Selection & StateUpdateTransitionRequired<States, Events, Emits, StateId, Context, Reenter, Selection> & ("declinable" extends Acceptance ? StateUpdateTransitionDeclinable<States, Events, Emits, StateId, Context, Reenter, Selection> : {});
|
|
3728
3854
|
/** @internal Type evidence retained by a machine initial-entry declaration. */
|
|
3729
3855
|
interface InitialBuilderEvidence<out Selection> {
|
|
3730
3856
|
readonly [InitialBuilderTypeId]: Types.Covariant<Selection>;
|
|
@@ -3748,7 +3874,7 @@ export declare namespace Machine {
|
|
|
3748
3874
|
type InitialSelector<States extends StateSchemas, Input = void> = InitialSelectorNode<Input, InitialTargetSelector<States>>;
|
|
3749
3875
|
/** Target-first initial-entry declaration accepted by {@link make}. */
|
|
3750
3876
|
type InitialBuilderInput<States extends StateSchemas, Input> = (to: InitialSelector<States, Input>) => InitialBuilderEvidence<TargetSelection<any, any, any>>;
|
|
3751
|
-
type TransitionSelectorNode<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean, Acceptance extends TransitionAcceptance, Node> = Node extends (...args: infer Args) => infer Selection ? Selection extends TargetSelection<any, any, any> ? ((...args: Args) => TransitionTarget<States, Events, Emits, StateId, Context, Reenter, Acceptance, Selection>) & {
|
|
3877
|
+
type TransitionSelectorNode<States extends StateSchemas, Events extends ReadonlyArray<TaggedSchema>, Emits extends ReadonlyArray<TaggedSchema>, StateId extends StateNodeIdentifier<States>, Context, Reenter extends boolean, Acceptance extends TransitionAcceptance, Node> = Node extends TargetSelection<any, any, "update"> ? StateUpdateTransition<States, Events, Emits, StateId, Context, Reenter, Acceptance, Node> : Node extends (...args: infer Args) => infer Selection ? Selection extends TargetSelection<any, any, any> ? ((...args: Args) => TransitionTarget<States, Events, Emits, StateId, Context, Reenter, Acceptance, Selection>) & {
|
|
3752
3878
|
readonly [Key in keyof Node]: TransitionSelectorNode<States, Events, Emits, StateId, Context, Reenter, Acceptance, Node[Key]>;
|
|
3753
3879
|
} : never : Node extends TargetSelection<any, any, any> ? TransitionTarget<States, Events, Emits, StateId, Context, Reenter, Acceptance, Node> : {
|
|
3754
3880
|
readonly [Key in keyof Node]: TransitionSelectorNode<States, Events, Emits, StateId, Context, Reenter, Acceptance, Node[Key]>;
|
|
@@ -4580,13 +4706,13 @@ interface Make {
|
|
|
4580
4706
|
* const counter = Machine.make({
|
|
4581
4707
|
* states: States.states,
|
|
4582
4708
|
* events: Events,
|
|
4583
|
-
* initial: (to) => to.Count().resolve(({ target }) => target(new Count({ value: 0 })))
|
|
4709
|
+
* initial: (to) => to.Count().resolve(({ target }) => target.decoded(new Count({ value: 0 })))
|
|
4584
4710
|
* }).handle({
|
|
4585
4711
|
* Count: {
|
|
4586
4712
|
* on: {
|
|
4587
4713
|
* Increment: (to) =>
|
|
4588
4714
|
* to.full.Count().resolve(({ event, state, target }) =>
|
|
4589
|
-
* target(new Count({ value: state.value + event.by })))
|
|
4715
|
+
* target.decoded(new Count({ value: state.value + event.by })))
|
|
4590
4716
|
* }
|
|
4591
4717
|
* }
|
|
4592
4718
|
* })
|
|
@@ -4810,7 +4936,16 @@ type TransitionBranchRecordError<Message extends string, Key extends PropertyKey
|
|
|
4810
4936
|
readonly key: Key;
|
|
4811
4937
|
};
|
|
4812
4938
|
type InvalidStaticTransitionBranchKey<Branches> = Extract<keyof Branches, "" | number | symbol>;
|
|
4813
|
-
type
|
|
4939
|
+
type InvalidUpdatingTransitionBranchKey<Branches> = {
|
|
4940
|
+
readonly [Key in keyof Branches]: Branches[Key] extends {
|
|
4941
|
+
readonly target: {
|
|
4942
|
+
readonly "~effect/Machine/UpdatingTransitionTarget": string;
|
|
4943
|
+
};
|
|
4944
|
+
} ? Key : never;
|
|
4945
|
+
}[keyof Branches];
|
|
4946
|
+
type ValidateTransitionBranchRecord<Branches> = [keyof Branches] extends [never] ? TransitionBranchRecordError<"Branch records must contain at least one branch"> : [InvalidStaticTransitionBranchKey<Branches>] extends [never] ? [
|
|
4947
|
+
InvalidUpdatingTransitionBranchKey<Branches>
|
|
4948
|
+
] extends [never] ? unknown : TransitionBranchRecordError<"Updating targets require a direct resolver", InvalidUpdatingTransitionBranchKey<Branches>> : TransitionBranchRecordError<"Branch keys must be non-empty, non-index strings", InvalidStaticTransitionBranchKey<Branches>>;
|
|
4814
4949
|
/**
|
|
4815
4950
|
* Plans the initial state for a machine without executing machine commands.
|
|
4816
4951
|
*
|
|
@@ -4908,9 +5043,10 @@ export declare const initialDefinition: <M extends Machine.Any>(machine: M) => M
|
|
|
4908
5043
|
*
|
|
4909
5044
|
* Event handlers retain their handler-key order within each source state and
|
|
4910
5045
|
* are followed by eventless and completion handlers. This function does not
|
|
4911
|
-
* execute resolvers. Every
|
|
4912
|
-
*
|
|
4913
|
-
*
|
|
5046
|
+
* execute resolvers. Every branch exposes its static selection. State updates
|
|
5047
|
+
* retain the updated owner in `selection.path` while leaving `target`
|
|
5048
|
+
* undefined because they do not change topology. `acceptance` reports whether
|
|
5049
|
+
* the resolver may decline the transition.
|
|
4914
5050
|
*
|
|
4915
5051
|
* @category getters
|
|
4916
5052
|
* @since 0.4.0
|