xstate 5.0.2 → 5.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (45) hide show
  1. package/actions/dist/xstate-actions.cjs.js +2 -2
  2. package/actions/dist/xstate-actions.development.cjs.js +2 -2
  3. package/actions/dist/xstate-actions.development.esm.js +2 -2
  4. package/actions/dist/xstate-actions.esm.js +2 -2
  5. package/actions/dist/xstate-actions.umd.min.js +1 -1
  6. package/actions/dist/xstate-actions.umd.min.js.map +1 -1
  7. package/actors/dist/xstate-actors.cjs.js +1 -1
  8. package/actors/dist/xstate-actors.development.cjs.js +1 -1
  9. package/actors/dist/xstate-actors.development.esm.js +1 -1
  10. package/actors/dist/xstate-actors.esm.js +1 -1
  11. package/actors/dist/xstate-actors.umd.min.js +1 -1
  12. package/actors/dist/xstate-actors.umd.min.js.map +1 -1
  13. package/dist/declarations/src/SimulatedClock.d.ts +3 -1
  14. package/dist/declarations/src/actions/send.d.ts +1 -1
  15. package/dist/declarations/src/actors/callback.d.ts +3 -2
  16. package/dist/declarations/src/actors/observable.d.ts +2 -1
  17. package/dist/declarations/src/actors/promise.d.ts +3 -2
  18. package/dist/declarations/src/actors/transition.d.ts +3 -2
  19. package/dist/declarations/src/index.d.ts +6 -5
  20. package/dist/declarations/src/interpreter.d.ts +4 -8
  21. package/dist/declarations/src/spawn.d.ts +3 -2
  22. package/dist/declarations/src/system.d.ts +32 -2
  23. package/dist/declarations/src/toPromise.d.ts +24 -0
  24. package/dist/declarations/src/types.d.ts +13 -16
  25. package/dist/{log-22e678c5.esm.js → log-5409ee89.esm.js} +15 -8
  26. package/dist/{log-f196f85f.development.esm.js → log-557e5fa3.development.esm.js} +15 -8
  27. package/dist/{log-5e226275.cjs.js → log-74467f02.cjs.js} +15 -8
  28. package/dist/{log-641cd926.development.cjs.js → log-a56e34a9.development.cjs.js} +15 -8
  29. package/dist/{raise-89c581c4.development.esm.js → raise-0ff85b7b.development.esm.js} +109 -43
  30. package/dist/{raise-8bc422d1.esm.js → raise-5d7ae4b7.esm.js} +109 -43
  31. package/dist/{raise-62704519.development.cjs.js → raise-6fb30f8b.development.cjs.js} +108 -42
  32. package/dist/{raise-34e25c2c.cjs.js → raise-746abff7.cjs.js} +108 -42
  33. package/dist/xstate.cjs.js +57 -5
  34. package/dist/xstate.cjs.mjs +1 -0
  35. package/dist/xstate.development.cjs.js +57 -5
  36. package/dist/xstate.development.cjs.mjs +1 -0
  37. package/dist/xstate.development.esm.js +59 -8
  38. package/dist/xstate.esm.js +59 -8
  39. package/dist/xstate.umd.min.js +1 -1
  40. package/dist/xstate.umd.min.js.map +1 -1
  41. package/guards/dist/xstate-guards.cjs.js +1 -1
  42. package/guards/dist/xstate-guards.development.cjs.js +1 -1
  43. package/guards/dist/xstate-guards.development.esm.js +1 -1
  44. package/guards/dist/xstate-guards.esm.js +1 -1
  45. package/package.json +1 -1
@@ -2,20 +2,21 @@ export * from "./actions.js";
2
2
  export * from "./actors/index.js";
3
3
  export { SimulatedClock } from "./SimulatedClock.js";
4
4
  export { type Spawner } from "./spawn.js";
5
+ export { isMachineSnapshot, type MachineSnapshot } from "./State.js";
5
6
  export { StateMachine } from "./StateMachine.js";
6
7
  export { getStateNodes } from "./stateUtils.js";
7
8
  export * from "./typegenTypes.js";
8
9
  export * from "./types.js";
9
10
  export { waitFor } from "./waitFor.js";
10
- import { Actor, createActor, interpret, Interpreter } from "./interpreter.js";
11
11
  import { createMachine } from "./createMachine.js";
12
- export { type MachineSnapshot, isMachineSnapshot } from "./State.js";
12
+ import { Actor, createActor, interpret, Interpreter } from "./interpreter.js";
13
13
  import { StateNode } from "./StateNode.js";
14
- export { matchesState, pathToStateValue, toObserver, getAllOwnEventDescriptors as __unsafe_getAllOwnEventDescriptors } from "./utils.js";
15
- export { Actor, createActor, createMachine, interpret, StateNode, type Interpreter };
16
- export type { InspectedActorEvent, InspectedEventEvent, InspectedSnapshotEvent, InspectionEvent } from "./system.js";
17
14
  export { and, not, or, stateIn } from "./guards.js";
18
15
  export { setup } from "./setup.js";
16
+ export type { ActorSystem, InspectedActorEvent, InspectedEventEvent, InspectedSnapshotEvent, InspectionEvent } from "./system.js";
17
+ export { toPromise } from "./toPromise.js";
18
+ export { getAllOwnEventDescriptors as __unsafe_getAllOwnEventDescriptors, matchesState, pathToStateValue, toObserver } from "./utils.js";
19
+ export { Actor, createActor, createMachine, interpret, StateNode, type Interpreter };
19
20
  declare global {
20
21
  interface SymbolConstructor {
21
22
  readonly observable: symbol;
@@ -1,16 +1,13 @@
1
1
  import { symbolObservable } from "./symbolObservable.js";
2
+ import { AnyActorSystem, Clock } from "./system.js";
2
3
  import { AreAllImplementationsAssumedToBeProvided, MissingImplementationsError } from "./typegenTypes.js";
3
- import type { ActorSystem, AnyActorLogic, AnyStateMachine, EventFromLogic, SnapshotFrom, Snapshot } from "./types.js";
4
- import { ActorRef, EventObject, InteropSubscribable, ActorOptions, Observer, Subscription } from "./types.js";
4
+ import type { AnyActorLogic, AnyStateMachine, EventFromLogic, Snapshot, SnapshotFrom } from "./types.js";
5
+ import { ActorOptions, ActorRef, EventObject, InteropSubscribable, Observer, Subscription } from "./types.js";
5
6
  export declare const $$ACTOR_TYPE = 1;
6
7
  export type SnapshotListener<TLogic extends AnyActorLogic> = (snapshot: SnapshotFrom<TLogic>) => void;
7
8
  export type EventListener<TEvent extends EventObject = EventObject> = (event: TEvent) => void;
8
9
  export type Listener = () => void;
9
10
  export type ErrorListener = (error: any) => void;
10
- export interface Clock {
11
- setTimeout(fn: (...args: any[]) => void, timeout: number): any;
12
- clearTimeout(id: any): void;
13
- }
14
11
  export declare enum ProcessingStatus {
15
12
  NotStarted = 0,
16
13
  Running = 1,
@@ -35,7 +32,6 @@ export declare class Actor<TLogic extends AnyActorLogic> implements ActorRef<Sna
35
32
  */
36
33
  id: string;
37
34
  private mailbox;
38
- private delayedEventsMap;
39
35
  private observers;
40
36
  private logger;
41
37
  _parent?: ActorRef<any, any>;
@@ -50,7 +46,7 @@ export declare class Actor<TLogic extends AnyActorLogic> implements ActorRef<Sna
50
46
  /**
51
47
  * The system to which this actor belongs.
52
48
  */
53
- system: ActorSystem<any>;
49
+ system: AnyActorSystem;
54
50
  private _doneEvent?;
55
51
  src: string | AnyActorLogic;
56
52
  /**
@@ -11,9 +11,10 @@ type SpawnOptions<TActor extends ProvidedActor, TSrc extends TActor['src']> = TA
11
11
  [K in RequiredActorOptions<TActor>]: unknown;
12
12
  }
13
13
  ], IsNotNever<RequiredActorOptions<TActor>>> : never;
14
- export type Spawner<TActor extends ProvidedActor> = IsLiteralString<TActor['src']> extends true ? <TSrc extends TActor['src']>(logic: TSrc, ...[options]: SpawnOptions<TActor, TSrc>) => ActorRefFrom<(TActor & {
14
+ type GetConcreteLogic<TActor extends ProvidedActor, TSrc extends TActor['src']> = Extract<TActor, {
15
15
  src: TSrc;
16
- })['logic']> : <TLogic extends AnyActorLogic | string>(src: TLogic, options?: {
16
+ }>['logic'];
17
+ export type Spawner<TActor extends ProvidedActor> = IsLiteralString<TActor['src']> extends true ? <TSrc extends TActor['src']>(logic: TSrc, ...[options]: SpawnOptions<TActor, TSrc>) => ActorRefFrom<GetConcreteLogic<TActor, TSrc>> : <TLogic extends AnyActorLogic | string>(src: TLogic, options?: {
17
18
  id?: string;
18
19
  systemId?: string;
19
20
  input?: unknown;
@@ -1,5 +1,35 @@
1
- import { AnyEventObject, ActorSystem, ActorSystemInfo, AnyActorRef, Snapshot } from "./types.js";
2
- export declare function createSystem<T extends ActorSystemInfo>(rootActor: AnyActorRef): ActorSystem<T>;
1
+ import { AnyEventObject, ActorSystemInfo, AnyActorRef, Observer, Snapshot, EventObject } from "./types.js";
2
+ export interface ScheduledEvent {
3
+ id: string;
4
+ event: EventObject;
5
+ startedAt: number;
6
+ delay: number;
7
+ source: AnyActorRef;
8
+ target: AnyActorRef;
9
+ }
10
+ export interface Clock {
11
+ setTimeout(fn: (...args: any[]) => void, timeout: number): any;
12
+ clearTimeout(id: any): void;
13
+ }
14
+ export interface Scheduler {
15
+ schedule(source: AnyActorRef, target: AnyActorRef, event: EventObject, delay: number, id: string | undefined): void;
16
+ cancel(source: AnyActorRef, id: string): void;
17
+ cancelAll(actorRef: AnyActorRef): void;
18
+ }
19
+ export interface ActorSystem<T extends ActorSystemInfo> {
20
+ get: <K extends keyof T['actors']>(key: K) => T['actors'][K] | undefined;
21
+ inspect: (observer: Observer<InspectionEvent>) => void;
22
+ scheduler: Scheduler;
23
+ getSnapshot: () => {
24
+ _scheduledEvents: Record<string, ScheduledEvent>;
25
+ };
26
+ start: () => void;
27
+ }
28
+ export type AnyActorSystem = ActorSystem<any>;
29
+ export declare function createSystem<T extends ActorSystemInfo>(rootActor: AnyActorRef, options: {
30
+ clock: Clock;
31
+ snapshot?: unknown;
32
+ }): ActorSystem<T>;
3
33
  export interface BaseInspectionEventProperties {
4
34
  rootId: string;
5
35
  /**
@@ -0,0 +1,24 @@
1
+ import { AnyActorRef, OutputFrom } from "./types.js";
2
+ /**
3
+ * Returns a promise that resolves to the `output` of the actor when it is done.
4
+ *
5
+ * @example
6
+ * ```ts
7
+ * const machine = createMachine({
8
+ * // ...
9
+ * output: {
10
+ * count: 42
11
+ * }
12
+ * });
13
+ *
14
+ * const actor = createActor(machine);
15
+ *
16
+ * actor.start();
17
+ *
18
+ * const output = await toPromise(actor);
19
+ *
20
+ * console.log(output);
21
+ * // logs { count: 42 }
22
+ * ```
23
+ */
24
+ export declare function toPromise<T extends AnyActorRef>(actor: T): Promise<OutputFrom<T>>;
@@ -1,13 +1,13 @@
1
- import type { StateNode } from "./StateNode.js";
2
1
  import type { MachineSnapshot } from "./State.js";
3
- import type { Clock, Actor } from "./interpreter.js";
4
2
  import type { StateMachine } from "./StateMachine.js";
5
- import { TypegenDisabled, ResolveTypegenMeta, TypegenConstraint, MarkAllImplementationsAsProvided, AreAllImplementationsAssumedToBeProvided } from "./typegenTypes.js";
3
+ import type { StateNode } from "./StateNode.js";
4
+ import { AssignArgs } from "./actions/assign.js";
6
5
  import { PromiseActorLogic } from "./actors/promise.js";
7
6
  import { Guard, GuardPredicate, UnknownGuard } from "./guards.js";
7
+ import type { Actor } from "./interpreter.js";
8
8
  import { Spawner } from "./spawn.js";
9
- import { AssignArgs } from "./actions/assign.js";
10
- import { InspectionEvent } from './system.js';
9
+ import { AnyActorSystem, InspectionEvent, Clock } from './system.js';
10
+ import { AreAllImplementationsAssumedToBeProvided, MarkAllImplementationsAsProvided, ResolveTypegenMeta, TypegenConstraint, TypegenDisabled } from "./typegenTypes.js";
11
11
  export type Identity<T> = {
12
12
  [K in keyof T]: T[K];
13
13
  };
@@ -82,7 +82,7 @@ export interface UnifiedArg<TContext extends MachineContext, TExpressionEvent ex
82
82
  event: TExpressionEvent;
83
83
  self: ActorRef<MachineSnapshot<TContext, TEvent, Record<string, AnyActorRef | undefined>, // TODO: this should be replaced with `TChildren`
84
84
  StateValue, string, unknown>, TEvent>;
85
- system: ActorSystem<any>;
85
+ system: AnyActorSystem;
86
86
  }
87
87
  export type MachineContext = Record<string, any>;
88
88
  export interface ActionArgs<TContext extends MachineContext, TExpressionEvent extends EventObject, TEvent extends EventObject> extends UnifiedArg<TContext, TExpressionEvent, TEvent> {
@@ -90,6 +90,8 @@ export interface ActionArgs<TContext extends MachineContext, TExpressionEvent ex
90
90
  export type InputFrom<T> = T extends StateMachine<infer _TContext, infer _TEvent, infer _TChildren, infer _TActor, infer _TAction, infer _TGuard, infer _TDelay, infer _TStateValue, infer _TTag, infer TInput, infer _TOutput, infer _TResolvedTypesMeta> ? TInput : T extends ActorLogic<infer _TSnapshot, infer _TEvent, infer TInput, infer _TSystem> ? TInput : never;
91
91
  export type OutputFrom<T> = T extends ActorLogic<infer TSnapshot, infer _TEvent, infer _TInput, infer _TSystem> ? (TSnapshot & {
92
92
  status: 'done';
93
+ })['output'] : T extends ActorRef<infer TSnapshot, infer _TEvent> ? (TSnapshot & {
94
+ status: 'done';
93
95
  })['output'] : never;
94
96
  export type ActionFunction<TContext extends MachineContext, TExpressionEvent extends EventObject, TEvent extends EventObject, TParams extends ParameterizedObject['params'] | undefined, TActor extends ProvidedActor, TAction extends ParameterizedObject, TGuard extends ParameterizedObject, TDelay extends string> = {
95
97
  (args: ActionArgs<TContext, TExpressionEvent, TEvent>, params: TParams): void;
@@ -746,7 +748,7 @@ export interface ActorRef<TSnapshot extends Snapshot<unknown>, TEvent extends Ev
746
748
  stop: () => void;
747
749
  toJSON?: () => any;
748
750
  _parent?: ActorRef<any, any>;
749
- system?: ActorSystem<any>;
751
+ system: AnyActorSystem;
750
752
  src: string | AnyActorLogic;
751
753
  }
752
754
  export type AnyActorRef = ActorRef<any, any>;
@@ -756,7 +758,7 @@ export type DevToolsAdapter = (service: AnyActor) => void;
756
758
  /**
757
759
  * @deprecated Use `Actor<T>` instead.
758
760
  */
759
- export type InterpreterFrom<T extends AnyStateMachine | ((...args: any[]) => AnyStateMachine)> = ReturnTypeOrValue<T> extends StateMachine<infer TContext, infer TEvent, infer TChildren, infer _TActor, infer _TAction, infer _TGuard, infer _TDelay, infer TStateValue, infer TTag, infer TInput, infer TOutput, infer TResolvedTypesMeta> ? Actor<ActorLogic<MachineSnapshot<TContext, TEvent, TChildren, TStateValue, TTag, TOutput, TResolvedTypesMeta>, TEvent, TInput, ActorSystem<any>>> : never;
761
+ export type InterpreterFrom<T extends AnyStateMachine | ((...args: any[]) => AnyStateMachine)> = ReturnTypeOrValue<T> extends StateMachine<infer TContext, infer TEvent, infer TChildren, infer _TActor, infer _TAction, infer _TGuard, infer _TDelay, infer TStateValue, infer TTag, infer TInput, infer TOutput, infer TResolvedTypesMeta> ? Actor<ActorLogic<MachineSnapshot<TContext, TEvent, TChildren, TStateValue, TTag, TOutput, TResolvedTypesMeta>, TEvent, TInput, AnyActorSystem>> : never;
760
762
  export type MachineImplementationsFrom<T extends AnyStateMachine | ((...args: any[]) => AnyStateMachine), TRequireMissingImplementations extends boolean = false> = ReturnTypeOrValue<T> extends StateMachine<infer TContext, infer _TEvent, infer _TChildren, infer _TActor, infer _TAction, infer _TGuard, infer _TDelay, infer _TStateValue, infer _TTag, infer _TInput, infer _TOutput, infer TResolvedTypesMeta> ? InternalMachineImplementations<TContext, TResolvedTypesMeta, TRequireMissingImplementations> : never;
761
763
  export type __ResolvedTypesMetaFrom<T> = T extends StateMachine<any, // context
762
764
  any, // event
@@ -769,7 +771,7 @@ any, // tag
769
771
  any, // input
770
772
  any, // output
771
773
  infer TResolvedTypesMeta> ? TResolvedTypesMeta : never;
772
- export interface ActorScope<TSnapshot extends Snapshot<unknown>, TEvent extends EventObject, TSystem extends ActorSystem<any> = ActorSystem<any>> {
774
+ export interface ActorScope<TSnapshot extends Snapshot<unknown>, TEvent extends EventObject, TSystem extends AnyActorSystem = AnyActorSystem> {
773
775
  self: ActorRef<TSnapshot, TEvent>;
774
776
  id: string;
775
777
  sessionId: string;
@@ -806,7 +808,7 @@ export type Snapshot<TOutput> = {
806
808
  */
807
809
  export interface ActorLogic<in out TSnapshot extends Snapshot<unknown>, // it's invariant because it's also part of `ActorScope["self"]["getSnapshot"]`
808
810
  in out TEvent extends EventObject, // it's invariant because it's also part of `ActorScope["self"]["send"]`
809
- in TInput = NonReducibleUnknown, TSystem extends ActorSystem<any> = ActorSystem<any>> {
811
+ in TInput = NonReducibleUnknown, TSystem extends AnyActorSystem = AnyActorSystem> {
810
812
  /** The initial setup/configuration used to create the actor logic. */
811
813
  config?: unknown;
812
814
  /**
@@ -851,7 +853,7 @@ export type AnyActorLogic = ActorLogic<any, // snapshot
851
853
  any, // event
852
854
  any, // input
853
855
  any>;
854
- export type UnknownActorLogic = ActorLogic<any, any, never, ActorSystem<any>>;
856
+ export type UnknownActorLogic = ActorLogic<any, any, never, AnyActorSystem>;
855
857
  export type SnapshotFrom<T> = ReturnTypeOrValue<T> extends infer R ? R extends ActorRef<infer TSnapshot, infer _> ? TSnapshot : R extends Actor<infer TLogic> ? SnapshotFrom<TLogic> : R extends ActorLogic<infer _, infer __, infer ___, infer ____> ? ReturnType<R['transition']> : R extends ActorScope<infer TSnapshot, infer _, infer __> ? TSnapshot : never : never;
856
858
  export type EventFromLogic<TLogic extends ActorLogic<any, any, any, any>> = TLogic extends ActorLogic<infer _, infer TEvent, infer __, infer _____> ? TEvent : never;
857
859
  type ResolveEventType<T> = ReturnTypeOrValue<T> extends infer R ? R extends StateMachine<infer _TContext, infer TEvent, infer _TChildren, infer _TActor, infer _TAction, infer _TGuard, infer _TDelay, infer _TStateValue, infer _TTag, infer _TInput, infer _TOutput, infer _TResolvedTypesMeta> ? TEvent : R extends MachineSnapshot<infer _TContext, infer TEvent, infer _TChildren, infer _TTag, infer _TOutput, infer _TResolvedTypesMeta> ? TEvent : R extends ActorRef<infer _, infer TEvent> ? TEvent : never : never;
@@ -870,11 +872,6 @@ export type TagsFrom<TMachine extends AnyStateMachine> = Parameters<StateFrom<TM
870
872
  export interface ActorSystemInfo {
871
873
  actors: Record<string, AnyActorRef>;
872
874
  }
873
- export interface ActorSystem<T extends ActorSystemInfo> {
874
- get: <K extends keyof T['actors']>(key: K) => T['actors'][K] | undefined;
875
- inspect: (observer: Observer<InspectionEvent>) => void;
876
- }
877
- export type AnyActorSystem = ActorSystem<any>;
878
875
  export type RequiredActorOptions<TActor extends ProvidedActor> = (undefined extends TActor['id'] ? never : 'id') | (undefined extends InputFrom<TActor['logic']> ? never : 'input');
879
876
  type ExtractLiteralString<T extends string | undefined> = T extends string ? string extends T ? never : T : never;
880
877
  type ToConcreteChildren<TActor extends ProvidedActor> = {
@@ -1,5 +1,8 @@
1
- import { R as ProcessingStatus, y as resolveReferencedActor, z as createActor, T as cloneMachineSnapshot, U as XSTATE_ERROR, V as createErrorActorEvent, e as evaluateGuard, L as cancel, M as raise, O as spawnChild, Q as stopChild } from './raise-8bc422d1.esm.js';
1
+ import { R as ProcessingStatus, y as resolveReferencedActor, z as createActor, T as cloneMachineSnapshot, U as XSTATE_ERROR, V as createErrorActorEvent, e as evaluateGuard, L as cancel, M as raise, O as spawnChild, Q as stopChild } from './raise-5d7ae4b7.esm.js';
2
2
 
3
+ // it's likely-ish that `(TActor & { src: TSrc })['logic']` would be faster
4
+ // but it's only possible to do it since https://github.com/microsoft/TypeScript/pull/53098 (TS 5.1)
5
+ // and we strive to support TS 5.0 whenever possible
3
6
  function createSpawner(actorScope, {
4
7
  machine,
5
8
  context
@@ -214,19 +217,23 @@ function retryResolveSendTo(_, snapshot, params) {
214
217
  }
215
218
  }
216
219
  function executeSendTo(actorScope, params) {
217
- if (typeof params.delay === 'number') {
218
- actorScope.self.delaySend(params);
219
- return;
220
- }
221
-
222
220
  // this forms an outgoing events queue
223
221
  // thanks to that the recipient actors are able to read the *updated* snapshot value of the sender
224
222
  actorScope.defer(() => {
225
223
  const {
226
224
  to,
227
- event
225
+ event,
226
+ delay,
227
+ id
228
228
  } = params;
229
- actorScope?.system._relay(actorScope.self, to, event.type === XSTATE_ERROR ? createErrorActorEvent(actorScope.self.id, event.data) : event);
229
+ if (typeof delay === 'number') {
230
+ actorScope.system.scheduler.schedule(actorScope.self, to, event, delay, id);
231
+ return;
232
+ }
233
+ actorScope.system._relay(actorScope.self,
234
+ // at this point, in a deferred task, it should already be mutated by retryResolveSendTo
235
+ // if it initially started as a string
236
+ to, event.type === XSTATE_ERROR ? createErrorActorEvent(actorScope.self.id, event.data) : event);
230
237
  });
231
238
  }
232
239
  /**
@@ -1,5 +1,8 @@
1
- import { R as ProcessingStatus, y as resolveReferencedActor, z as createActor, T as cloneMachineSnapshot, U as XSTATE_ERROR, V as createErrorActorEvent, e as evaluateGuard, L as cancel, M as raise, O as spawnChild, Q as stopChild } from './raise-89c581c4.development.esm.js';
1
+ import { R as ProcessingStatus, y as resolveReferencedActor, z as createActor, T as cloneMachineSnapshot, U as XSTATE_ERROR, V as createErrorActorEvent, e as evaluateGuard, L as cancel, M as raise, O as spawnChild, Q as stopChild } from './raise-0ff85b7b.development.esm.js';
2
2
 
3
+ // it's likely-ish that `(TActor & { src: TSrc })['logic']` would be faster
4
+ // but it's only possible to do it since https://github.com/microsoft/TypeScript/pull/53098 (TS 5.1)
5
+ // and we strive to support TS 5.0 whenever possible
3
6
  function createSpawner(actorScope, {
4
7
  machine,
5
8
  context
@@ -217,19 +220,23 @@ function retryResolveSendTo(_, snapshot, params) {
217
220
  }
218
221
  }
219
222
  function executeSendTo(actorScope, params) {
220
- if (typeof params.delay === 'number') {
221
- actorScope.self.delaySend(params);
222
- return;
223
- }
224
-
225
223
  // this forms an outgoing events queue
226
224
  // thanks to that the recipient actors are able to read the *updated* snapshot value of the sender
227
225
  actorScope.defer(() => {
228
226
  const {
229
227
  to,
230
- event
228
+ event,
229
+ delay,
230
+ id
231
231
  } = params;
232
- actorScope?.system._relay(actorScope.self, to, event.type === XSTATE_ERROR ? createErrorActorEvent(actorScope.self.id, event.data) : event);
232
+ if (typeof delay === 'number') {
233
+ actorScope.system.scheduler.schedule(actorScope.self, to, event, delay, id);
234
+ return;
235
+ }
236
+ actorScope.system._relay(actorScope.self,
237
+ // at this point, in a deferred task, it should already be mutated by retryResolveSendTo
238
+ // if it initially started as a string
239
+ to, event.type === XSTATE_ERROR ? createErrorActorEvent(actorScope.self.id, event.data) : event);
233
240
  });
234
241
  }
235
242
  /**
@@ -1,7 +1,10 @@
1
1
  'use strict';
2
2
 
3
- var guards_dist_xstateGuards = require('./raise-34e25c2c.cjs.js');
3
+ var guards_dist_xstateGuards = require('./raise-746abff7.cjs.js');
4
4
 
5
+ // it's likely-ish that `(TActor & { src: TSrc })['logic']` would be faster
6
+ // but it's only possible to do it since https://github.com/microsoft/TypeScript/pull/53098 (TS 5.1)
7
+ // and we strive to support TS 5.0 whenever possible
5
8
  function createSpawner(actorScope, {
6
9
  machine,
7
10
  context
@@ -216,19 +219,23 @@ function retryResolveSendTo(_, snapshot, params) {
216
219
  }
217
220
  }
218
221
  function executeSendTo(actorScope, params) {
219
- if (typeof params.delay === 'number') {
220
- actorScope.self.delaySend(params);
221
- return;
222
- }
223
-
224
222
  // this forms an outgoing events queue
225
223
  // thanks to that the recipient actors are able to read the *updated* snapshot value of the sender
226
224
  actorScope.defer(() => {
227
225
  const {
228
226
  to,
229
- event
227
+ event,
228
+ delay,
229
+ id
230
230
  } = params;
231
- actorScope?.system._relay(actorScope.self, to, event.type === guards_dist_xstateGuards.XSTATE_ERROR ? guards_dist_xstateGuards.createErrorActorEvent(actorScope.self.id, event.data) : event);
231
+ if (typeof delay === 'number') {
232
+ actorScope.system.scheduler.schedule(actorScope.self, to, event, delay, id);
233
+ return;
234
+ }
235
+ actorScope.system._relay(actorScope.self,
236
+ // at this point, in a deferred task, it should already be mutated by retryResolveSendTo
237
+ // if it initially started as a string
238
+ to, event.type === guards_dist_xstateGuards.XSTATE_ERROR ? guards_dist_xstateGuards.createErrorActorEvent(actorScope.self.id, event.data) : event);
232
239
  });
233
240
  }
234
241
  /**
@@ -1,7 +1,10 @@
1
1
  'use strict';
2
2
 
3
- var guards_dist_xstateGuards = require('./raise-62704519.development.cjs.js');
3
+ var guards_dist_xstateGuards = require('./raise-6fb30f8b.development.cjs.js');
4
4
 
5
+ // it's likely-ish that `(TActor & { src: TSrc })['logic']` would be faster
6
+ // but it's only possible to do it since https://github.com/microsoft/TypeScript/pull/53098 (TS 5.1)
7
+ // and we strive to support TS 5.0 whenever possible
5
8
  function createSpawner(actorScope, {
6
9
  machine,
7
10
  context
@@ -219,19 +222,23 @@ function retryResolveSendTo(_, snapshot, params) {
219
222
  }
220
223
  }
221
224
  function executeSendTo(actorScope, params) {
222
- if (typeof params.delay === 'number') {
223
- actorScope.self.delaySend(params);
224
- return;
225
- }
226
-
227
225
  // this forms an outgoing events queue
228
226
  // thanks to that the recipient actors are able to read the *updated* snapshot value of the sender
229
227
  actorScope.defer(() => {
230
228
  const {
231
229
  to,
232
- event
230
+ event,
231
+ delay,
232
+ id
233
233
  } = params;
234
- actorScope?.system._relay(actorScope.self, to, event.type === guards_dist_xstateGuards.XSTATE_ERROR ? guards_dist_xstateGuards.createErrorActorEvent(actorScope.self.id, event.data) : event);
234
+ if (typeof delay === 'number') {
235
+ actorScope.system.scheduler.schedule(actorScope.self, to, event, delay, id);
236
+ return;
237
+ }
238
+ actorScope.system._relay(actorScope.self,
239
+ // at this point, in a deferred task, it should already be mutated by retryResolveSendTo
240
+ // if it initially started as a string
241
+ to, event.type === guards_dist_xstateGuards.XSTATE_ERROR ? guards_dist_xstateGuards.createErrorActorEvent(actorScope.self.id, event.data) : event);
235
242
  });
236
243
  }
237
244
  /**
@@ -126,13 +126,56 @@ function reportUnhandledError(err) {
126
126
 
127
127
  const symbolObservable = (() => typeof Symbol === 'function' && Symbol.observable || '@@observable')();
128
128
 
129
+ function createScheduledEventId(actorRef, id) {
130
+ return `${actorRef.sessionId}.${id}`;
131
+ }
129
132
  let idCounter = 0;
130
- function createSystem(rootActor) {
133
+ function createSystem(rootActor, options) {
131
134
  const children = new Map();
132
135
  const keyedActors = new Map();
133
136
  const reverseKeyedActors = new WeakMap();
134
137
  const observers = new Set();
138
+ const timerMap = {};
139
+ const clock = options.clock;
140
+ const scheduler = {
141
+ schedule: (source, target, event, delay, id = Math.random().toString(36).slice(2)) => {
142
+ const scheduledEvent = {
143
+ source,
144
+ target,
145
+ event,
146
+ delay,
147
+ id,
148
+ startedAt: Date.now()
149
+ };
150
+ const scheduledEventId = createScheduledEventId(source, id);
151
+ system._snapshot._scheduledEvents[scheduledEventId] = scheduledEvent;
152
+ const timeout = clock.setTimeout(() => {
153
+ delete timerMap[scheduledEventId];
154
+ delete system._snapshot._scheduledEvents[scheduledEventId];
155
+ system._relay(source, target, event);
156
+ }, delay);
157
+ timerMap[scheduledEventId] = timeout;
158
+ },
159
+ cancel: (source, id) => {
160
+ const scheduledEventId = createScheduledEventId(source, id);
161
+ const timeout = timerMap[scheduledEventId];
162
+ delete timerMap[scheduledEventId];
163
+ delete system._snapshot._scheduledEvents[scheduledEventId];
164
+ clock.clearTimeout(timeout);
165
+ },
166
+ cancelAll: actorRef => {
167
+ for (const scheduledEventId in system._snapshot._scheduledEvents) {
168
+ const scheduledEvent = system._snapshot._scheduledEvents[scheduledEventId];
169
+ if (scheduledEvent.source === actorRef) {
170
+ scheduler.cancel(actorRef, scheduledEvent.id);
171
+ }
172
+ }
173
+ }
174
+ };
135
175
  const system = {
176
+ _snapshot: {
177
+ _scheduledEvents: (options?.snapshot && options.snapshot.scheduler) ?? {}
178
+ },
136
179
  _bookId: () => `x:${idCounter++}`,
137
180
  _register: (sessionId, actorRef) => {
138
181
  children.set(sessionId, actorRef);
@@ -175,6 +218,28 @@ function createSystem(rootActor) {
175
218
  event
176
219
  });
177
220
  target._send(event);
221
+ },
222
+ scheduler,
223
+ getSnapshot: () => {
224
+ return {
225
+ _scheduledEvents: {
226
+ ...system._snapshot._scheduledEvents
227
+ }
228
+ };
229
+ },
230
+ start: () => {
231
+ const scheduledEvets = system._snapshot._scheduledEvents;
232
+ system._snapshot._scheduledEvents = {};
233
+ for (const scheduledId in scheduledEvets) {
234
+ const {
235
+ source,
236
+ target,
237
+ event,
238
+ delay,
239
+ id
240
+ } = scheduledEvets[scheduledId];
241
+ scheduler.schedule(source, target, event, delay, id);
242
+ }
178
243
  }
179
244
  };
180
245
  return system;
@@ -363,7 +428,6 @@ class Actor {
363
428
  */
364
429
  this.id = void 0;
365
430
  this.mailbox = new Mailbox(this._process.bind(this));
366
- this.delayedEventsMap = {};
367
431
  this.observers = new Set();
368
432
  this.logger = void 0;
369
433
  /** @internal */
@@ -400,7 +464,9 @@ class Actor {
400
464
  systemId,
401
465
  inspect
402
466
  } = resolvedOptions;
403
- this.system = parent?.system ?? createSystem(this);
467
+ this.system = parent ? parent.system : createSystem(this, {
468
+ clock
469
+ });
404
470
  if (inspect && !parent) {
405
471
  // Always inspect at the system-level
406
472
  this.system.inspect(toObserver(inspect));
@@ -581,10 +647,28 @@ class Actor {
581
647
  if (this._processingStatus !== ProcessingStatus.Stopped) {
582
648
  this.observers.add(observer);
583
649
  } else {
584
- try {
585
- observer.complete?.();
586
- } catch (err) {
587
- reportUnhandledError(err);
650
+ switch (this._snapshot.status) {
651
+ case 'done':
652
+ try {
653
+ observer.complete?.();
654
+ } catch (err) {
655
+ reportUnhandledError(err);
656
+ }
657
+ break;
658
+ case 'error':
659
+ {
660
+ const err = this._snapshot.error;
661
+ if (!observer.error) {
662
+ reportUnhandledError(err);
663
+ } else {
664
+ try {
665
+ observer.error(err);
666
+ } catch (err) {
667
+ reportUnhandledError(err);
668
+ }
669
+ }
670
+ break;
671
+ }
588
672
  }
589
673
  }
590
674
  return {
@@ -641,6 +725,9 @@ class Actor {
641
725
  this._error(this._snapshot.error);
642
726
  return this;
643
727
  }
728
+ if (!this._parent) {
729
+ this.system.start();
730
+ }
644
731
  if (this.logic.start) {
645
732
  try {
646
733
  this.logic.start(this._snapshot, this._actorScope);
@@ -769,9 +856,7 @@ class Actor {
769
856
  }
770
857
 
771
858
  // Cancel all delayed events
772
- for (const key of Object.keys(this.delayedEventsMap)) {
773
- this.clock.clearTimeout(this.delayedEventsMap[key]);
774
- }
859
+ this.system.scheduler.cancelAll(this);
775
860
 
776
861
  // TODO: mailbox.reset
777
862
  this.mailbox.clear();
@@ -811,35 +896,6 @@ class Actor {
811
896
  }
812
897
  this.system._relay(undefined, this, event);
813
898
  }
814
-
815
- /**
816
- * TODO: figure out a way to do this within the machine
817
- * @internal
818
- */
819
- delaySend(params) {
820
- const {
821
- event,
822
- id,
823
- delay
824
- } = params;
825
- const timerId = this.clock.setTimeout(() => {
826
- this.system._relay(this, params.to ?? this, event);
827
- }, delay);
828
-
829
- // TODO: consider the rehydration story here
830
- if (id) {
831
- this.delayedEventsMap[id] = timerId;
832
- }
833
- }
834
-
835
- /**
836
- * TODO: figure out a way to do this within the machine
837
- * @internal
838
- */
839
- cancel(sendId) {
840
- this.clock.clearTimeout(this.delayedEventsMap[sendId]);
841
- delete this.delayedEventsMap[sendId];
842
- }
843
899
  attachDevTools() {
844
900
  const {
845
901
  devTools
@@ -951,7 +1007,9 @@ function resolveCancel(_, snapshot, actionArgs, actionParams, {
951
1007
  return [snapshot, resolvedSendId];
952
1008
  }
953
1009
  function executeCancel(actorScope, resolvedSendId) {
954
- actorScope.self.cancel(resolvedSendId);
1010
+ actorScope.defer(() => {
1011
+ actorScope.system.scheduler.cancel(actorScope.self, resolvedSendId);
1012
+ });
955
1013
  }
956
1014
  /**
957
1015
  * Cancels an in-flight `send(...)` action. A canceled sent action will not
@@ -2342,8 +2400,16 @@ function resolveRaise(_, snapshot, args, actionParams, {
2342
2400
  }];
2343
2401
  }
2344
2402
  function executeRaise(actorScope, params) {
2345
- if (typeof params.delay === 'number') {
2346
- actorScope.self.delaySend(params);
2403
+ const {
2404
+ event,
2405
+ delay,
2406
+ id
2407
+ } = params;
2408
+ if (typeof delay === 'number') {
2409
+ actorScope.defer(() => {
2410
+ const self = actorScope.self;
2411
+ actorScope.system.scheduler.schedule(self, self, event, delay, id);
2412
+ });
2347
2413
  return;
2348
2414
  }
2349
2415
  }
@@ -2368,4 +2434,4 @@ function raise(eventOrExpr, options) {
2368
2434
  return raise;
2369
2435
  }
2370
2436
 
2371
- export { $$ACTOR_TYPE as $, Actor as A, interpret as B, isMachineSnapshot as C, matchesState as D, pathToStateValue as E, toObserver as F, getAllOwnEventDescriptors as G, and as H, not as I, or as J, stateIn as K, cancel as L, raise as M, NULL_EVENT as N, spawnChild as O, stop as P, stopChild as Q, ProcessingStatus as R, STATE_DELIMITER as S, cloneMachineSnapshot as T, XSTATE_ERROR as U, createErrorActorEvent as V, XSTATE_STOP as X, toTransitionConfigArray as a, formatTransition as b, createInvokeId as c, formatInitialTransition as d, evaluateGuard as e, formatTransitions as f, getDelayedTransitions as g, getCandidates as h, getAllStateNodes as i, getStateNodes as j, createMachineSnapshot as k, isInFinalState as l, mapValues as m, macrostep as n, transitionNode as o, resolveActionsAndContext as p, createInitEvent as q, resolveStateValue as r, microstep as s, toArray as t, getInitialStateNodes as u, isStateId as v, getStateNodeByPath as w, getPersistedSnapshot as x, resolveReferencedActor as y, createActor as z };
2437
+ export { $$ACTOR_TYPE as $, Actor as A, interpret as B, isMachineSnapshot as C, and as D, not as E, or as F, stateIn as G, getAllOwnEventDescriptors as H, matchesState as I, pathToStateValue as J, toObserver as K, cancel as L, raise as M, NULL_EVENT as N, spawnChild as O, stop as P, stopChild as Q, ProcessingStatus as R, STATE_DELIMITER as S, cloneMachineSnapshot as T, XSTATE_ERROR as U, createErrorActorEvent as V, XSTATE_STOP as X, toTransitionConfigArray as a, formatTransition as b, createInvokeId as c, formatInitialTransition as d, evaluateGuard as e, formatTransitions as f, getDelayedTransitions as g, getCandidates as h, getAllStateNodes as i, getStateNodes as j, createMachineSnapshot as k, isInFinalState as l, mapValues as m, macrostep as n, transitionNode as o, resolveActionsAndContext as p, createInitEvent as q, resolveStateValue as r, microstep as s, toArray as t, getInitialStateNodes as u, isStateId as v, getStateNodeByPath as w, getPersistedSnapshot as x, resolveReferencedActor as y, createActor as z };