import type { MachineSnapshot } from "./State.js"; import type { StateMachine } from "./StateMachine.js"; import type { StateNode } from "./StateNode.js"; import { AssignArgs } from "./actions/assign.js"; import { PromiseActorLogic } from "./actors/promise.js"; import { Guard, GuardPredicate, UnknownGuard } from "./guards.js"; import type { Actor } from "./createActor.js"; import { Spawner } from "./spawn.js"; import { AnyActorSystem, Clock } from './system.js'; import { InspectionEvent } from "./inspection.js"; import { ExecutableRaiseAction } from "./actions/raise.js"; import { ExecutableSendToAction } from "./actions/send.js"; export type Identity = { [K in keyof T]: T[K]; }; export type HomomorphicPick = { [P in keyof T as P & K]: T[P]; }; export type HomomorphicOmit = { [P in keyof T as Exclude]: T[P]; }; export type Invert> = { [K in keyof T as T[K]]: K; }; export type GetParameterizedParams = T extends any ? ('params' extends keyof T ? T['params'] : undefined) : never; /** * @remarks * `T | unknown` reduces to `unknown` and that can be problematic when it comes * to contextual typing. It especially is a problem when the union has a * function member, like here: * * ```ts * declare function test( * cbOrVal: ((arg: number) => unknown) | unknown * ): void; * test((arg) => {}); // oops, implicit any * ``` * * This type can be used to avoid this problem. This union represents the same * value space as `unknown`. */ export type NonReducibleUnknown = {} | null | undefined; export type AnyFunction = (...args: any[]) => any; type ReturnTypeOrValue = T extends AnyFunction ? ReturnType : T; export type IsNever = [T] extends [never] ? true : false; export type IsNotNever = [T] extends [never] ? false : true; export type Compute = { [K in keyof A]: A[K]; } & unknown; export type Prop = K extends keyof T ? T[K] : never; export type Values = T[keyof T]; export type Elements = T[keyof T & `${number}`]; export type Merge = Omit & N; export type IndexByProp, P extends keyof T> = { [E in T as E[P]]: E; }; export type IndexByType = IndexByProp; export type Equals = (() => A extends A2 ? true : false) extends () => A extends A1 ? true : false ? true : false; export type IsAny = Equals; export type Cast = A extends B ? A : B; export type DoNotInfer = [T][T extends any ? 0 : any]; /** @deprecated Use the built-in `NoInfer` type instead */ export type NoInfer = DoNotInfer; export type LowInfer = T & NonNullable; export type MetaObject = Record; export type Lazy = () => T; export type MaybeLazy = T | Lazy; /** The full definition of an event, with a string `type`. */ export type EventObject = { /** The type of event that is sent. */ type: string; }; export interface AnyEventObject extends EventObject { [key: string]: any; } export interface ParameterizedObject { type: string; params?: NonReducibleUnknown; } export interface UnifiedArg { context: TContext; event: TExpressionEvent; self: ActorRef, // TODO: this should be replaced with `TChildren` StateValue, string, unknown, TODO, // TMeta TODO>, TEvent, AnyEventObject>; system: AnyActorSystem; } export type MachineContext = Record; export interface ActionArgs extends UnifiedArg { } export type InputFrom = T extends StateMachine ? TInput : T extends ActorLogic ? TInput : never; export type OutputFrom = T extends ActorLogic ? (TSnapshot & { status: 'done'; })['output'] : T extends ActorRef ? (TSnapshot & { status: 'done'; })['output'] : never; export type ActionFunction = { (args: ActionArgs, params: TParams): void; _out_TEvent?: TEvent; _out_TActor?: TActor; _out_TAction?: TAction; _out_TGuard?: TGuard; _out_TDelay?: TDelay; _out_TEmitted?: TEmitted; }; export type NoRequiredParams = T extends any ? undefined extends T['params'] ? T['type'] : never : never; export type ConditionalRequired = Condition extends true ? Required : T; export type WithDynamicParams = T extends any ? ConditionalRequired<{ type: T['type']; params?: T['params'] | (({ context, event }: { context: TContext; event: TExpressionEvent; }) => T['params']); }, undefined extends T['params'] ? false : true> : never; export type Action = NoRequiredParams | WithDynamicParams | ActionFunction; export type UnknownAction = Action; export type Actions = SingleOrArray>; export type StateKey = string | AnyMachineSnapshot; export interface StateValueMap { [key: string]: StateValue | undefined; } /** * The string or object representing the state value relative to the parent * state node. * * @remarks * - For a child atomic state node, this is a string, e.g., `"pending"`. * - For complex state nodes, this is an object, e.g., `{ success: * "someChildState" }`. */ export type StateValue = string | StateValueMap; export type TransitionTarget = SingleOrArray; export interface TransitionConfig { guard?: Guard; actions?: Actions; reenter?: boolean; target?: TransitionTarget | undefined; meta?: TMeta; description?: string; } export interface InitialTransitionConfig extends TransitionConfig { target: string; } export type AnyTransitionConfig = TransitionConfig; export interface InvokeDefinition { id: string; systemId: string | undefined; /** The source of the actor logic to be invoked */ src: AnyActorLogic | string; input?: Mapper | NonReducibleUnknown; /** * The transition to take upon the invoked child machine reaching its final * top-level state. */ onDone?: string | SingleOrArray, TEvent, TActor, TAction, TGuard, TDelay, TEmitted, TMeta>>; /** * The transition to take upon the invoked child machine sending an error * event. */ onError?: string | SingleOrArray>; onSnapshot?: string | SingleOrArray>; toJSON: () => Omit, 'onDone' | 'onError' | 'toJSON'>; } type Delay = TDelay | number; export type DelayedTransitions = { [K in Delay]?: string | SingleOrArray>; }; export type StateTypes = 'atomic' | 'compound' | 'parallel' | 'final' | 'history' | ({} & string); export type SingleOrArray = readonly T[] | T; export type StateNodesConfig = { [K in string]: StateNode; }; export type StatesConfig = { [K in string]: StateNodeConfig; }; export type StatesDefinition = { [K in string]: StateNodeDefinition; }; export type TransitionConfigTarget = string | undefined; export type TransitionConfigOrTarget = SingleOrArray>; export type TransitionsConfig = { [K in EventDescriptor]?: TransitionConfigOrTarget, TEvent, TActor, TAction, TGuard, TDelay, TEmitted, TMeta>; }; type PartialEventDescriptor = TEventType extends `${infer TLeading}.${infer TTail}` ? `${TLeading}.*` | `${TLeading}.${PartialEventDescriptor}` : never; export type EventDescriptor = TEvent['type'] | PartialEventDescriptor | '*'; type NormalizeDescriptor = TDescriptor extends '*' ? string : TDescriptor extends `${infer TLeading}.*` ? `${TLeading}.${string}` : TDescriptor; export type IsLiteralString = string extends T ? false : true; type DistributeActors = TSpecificActor extends { src: infer TSrc; } ? Compute<{ systemId?: string; /** The source of the machine to be invoked, or the machine itself. */ src: TSrc; /** * The unique identifier for the invoked machine. If not specified, * this will be the machine's own `id`, or the URL (from `src`). */ id?: TSpecificActor['id']; input?: Mapper, TEvent> | InputFrom; /** * The transition to take upon the invoked child machine reaching * its final top-level state. */ onDone?: string | SingleOrArray>, TEvent, TActor, TAction, TGuard, TDelay, TEmitted, TMeta>>; /** * The transition to take upon the invoked child machine sending an * error event. */ onError?: string | SingleOrArray>; onSnapshot?: string | SingleOrArray>, TEvent, TActor, TAction, TGuard, TDelay, TEmitted, TMeta>>; } & { [K in RequiredActorOptions]: unknown; }> | { id?: never; systemId?: string; src: AnyActorLogic; input?: Mapper | NonReducibleUnknown; onDone?: string | SingleOrArray, TEvent, TActor, TAction, TGuard, TDelay, TEmitted, TMeta>>; onError?: string | SingleOrArray>; onSnapshot?: string | SingleOrArray>; } : never; export type InvokeConfig = IsLiteralString extends true ? DistributeActors : { /** * The unique identifier for the invoked machine. If not specified, this * will be the machine's own `id`, or the URL (from `src`). */ id?: string; systemId?: string; /** The source of the machine to be invoked, or the machine itself. */ src: AnyActorLogic | string; input?: Mapper | NonReducibleUnknown; /** * The transition to take upon the invoked child machine reaching its * final top-level state. */ onDone?: string | SingleOrArray, // TODO: consider replacing with `unknown` TEvent, TActor, TAction, TGuard, TDelay, TEmitted, TMeta>>; /** * The transition to take upon the invoked child machine sending an * error event. */ onError?: string | SingleOrArray>; onSnapshot?: string | SingleOrArray>; }; export type AnyInvokeConfig = InvokeConfig; export interface StateNodeConfig { /** The initial state transition. */ initial?: InitialTransitionConfig | string | undefined; /** * The type of this state node: * * - `'atomic'` - no child state nodes * - `'compound'` - nested child state nodes (XOR) * - `'parallel'` - orthogonal nested child state nodes (AND) * - `'history'` - history state node * - `'final'` - final state node */ type?: 'atomic' | 'compound' | 'parallel' | 'final' | 'history'; /** * Indicates whether the state node is a history state node, and what type of * history: shallow, deep, true (shallow), false (none), undefined (none) */ history?: 'shallow' | 'deep' | boolean | undefined; /** * The mapping of state node keys to their state node configurations * (recursive). */ states?: StatesConfig | undefined; /** * The services to invoke upon entering this state node. These services will * be stopped upon exiting this state node. */ invoke?: SingleOrArray>; /** The mapping of event types to their potential transition(s). */ on?: TransitionsConfig; /** The action(s) to be executed upon entering the state node. */ entry?: Actions; /** The action(s) to be executed upon exiting the state node. */ exit?: Actions; /** * The potential transition(s) to be taken upon reaching a final child state * node. * * This is equivalent to defining a `[done(id)]` transition on this state * node's `on` property. */ onDone?: string | SingleOrArray> | undefined; /** * The mapping (or array) of delays (in milliseconds) to their potential * transition(s). The delayed transitions are taken after the specified delay * in an interpreter. */ after?: DelayedTransitions; /** * An eventless transition that is always taken when this state node is * active. */ always?: TransitionConfigOrTarget; parent?: StateNode; /** * The meta data associated with this state node, which will be returned in * State instances. */ meta?: TMeta; /** * The output data sent with the "xstate.done.state._id_" event if this is a * final state node. * * The output data will be evaluated with the current `context` and placed on * the `.data` property of the event. */ output?: Mapper | NonReducibleUnknown; /** * The unique ID of the state node, which can be referenced as a transition * target via the `#id` syntax. */ id?: string | undefined; /** * The order this state node appears. Corresponds to the implicit document * order. */ order?: number; /** * The tags for this state node, which are accumulated into the `state.tags` * property. */ tags?: SingleOrArray; /** A text description of the state node */ description?: string; /** A default target for a history state */ target?: string; } export type AnyStateNodeConfig = StateNodeConfig; export interface StateNodeDefinition { id: string; version?: string | undefined; key: string; type: 'atomic' | 'compound' | 'parallel' | 'final' | 'history'; initial: InitialTransitionDefinition | undefined; history: boolean | 'shallow' | 'deep' | undefined; states: StatesDefinition; on: TransitionDefinitionMap; transitions: Array>; entry: UnknownAction[]; exit: UnknownAction[]; meta: any; order: number; output?: StateNodeConfig['output']; invoke: Array>; description?: string; tags: string[]; } export interface StateMachineDefinition extends StateNodeDefinition { } export type AnyStateNode = StateNode; export type AnyStateNodeDefinition = StateNodeDefinition; export type AnyMachineSnapshot = MachineSnapshot; /** @deprecated Use `AnyMachineSnapshot` instead */ export type AnyState = AnyMachineSnapshot; export type AnyStateMachine = StateMachine; export type AnyStateConfig = StateConfig; export interface AtomicStateNodeConfig extends StateNodeConfig { initial?: undefined; parallel?: false | undefined; states?: undefined; onDone?: undefined; } export interface HistoryStateNodeConfig extends AtomicStateNodeConfig { history: 'shallow' | 'deep' | true; target: string | undefined; } export type SimpleOrStateNodeConfig = AtomicStateNodeConfig | StateNodeConfig; export type ActionFunctionMap = { [K in TAction['type']]?: ActionFunction, TActor, TAction, TGuard, TDelay, TEmitted>; }; type GuardMap = { [K in TGuard['type']]?: GuardPredicate, TGuard>; }; export type DelayFunctionMap = Record>; export type DelayConfig = number | DelayExpr; /** @ignore */ export interface MachineImplementationsSimplified { guards: GuardMap; actions: ActionFunctionMap; actors: Record | NonReducibleUnknown; }>; delays: DelayFunctionMap; } type MachineImplementationsActions = { [K in TTypes['actions']['type']]?: ActionFunction['params'], TTypes['actors'], TTypes['actions'], TTypes['guards'], TTypes['delays'], TTypes['emitted']>; }; type MachineImplementationsActors = { [K in TTypes['actors']['src']]?: GetConcreteByKey['logic']; }; type MachineImplementationsDelays = { [K in TTypes['delays']]?: DelayConfig; }; type MachineImplementationsGuards = { [K in TTypes['guards']['type']]?: Guard['params'], TTypes['guards']>; }; export type InternalMachineImplementations = { actions?: MachineImplementationsActions; actors?: MachineImplementationsActors; delays?: MachineImplementationsDelays; guards?: MachineImplementationsGuards; }; type InitialContext = TContext | ContextFactory; export type ContextFactory = ({ spawn, input, self }: { spawn: Spawner; input: TInput; self: ActorRef, // TODO: this should be replaced with `TChildren` StateValue, string, unknown, TODO, // TMeta TODO>, TEvent, AnyEventObject>; }) => TContext; export type MachineConfig = (Omit, DoNotInfer, DoNotInfer, DoNotInfer, DoNotInfer, DoNotInfer, DoNotInfer, DoNotInfer, DoNotInfer, DoNotInfer>, 'output'> & { /** The initial context (extended state) */ /** The machine's own version. */ version?: string; output?: Mapper | TOutput; }) & (MachineContext extends TContext ? { context?: InitialContext, TActor, TInput, TEvent>; } : { context: InitialContext, TActor, TInput, TEvent>; }); export type UnknownMachineConfig = MachineConfig; export interface ProvidedActor { src: string; logic: UnknownActorLogic; id?: string; } export interface SetupTypes, TTag extends string, TInput, TOutput, TEmitted extends EventObject, TMeta extends MetaObject> { context?: TContext; events?: TEvent; children?: TChildrenMap; tags?: TTag; input?: TInput; output?: TOutput; emitted?: TEmitted; meta?: TMeta; } export interface MachineTypes extends SetupTypes { actors?: TActor; actions?: TAction; guards?: TGuard; delays?: TDelay; meta?: TMeta; } export interface HistoryStateNode extends StateNode { history: 'shallow' | 'deep'; target: string | undefined; } export type HistoryValue = Record>>; export type AnyHistoryValue = HistoryValue; export type StateFrom AnyStateMachine)> = T extends AnyStateMachine ? ReturnType : T extends (...args: any[]) => AnyStateMachine ? ReturnType['transition']> : never; export type Transitions = Array>; export interface DoneActorEvent extends EventObject { type: `xstate.done.actor.${TId}`; output: TOutput; actorId: TId; } export interface ErrorActorEvent extends EventObject { type: `xstate.error.actor.${TId}`; error: TErrorData; actorId: TId; } export interface SnapshotEvent = Snapshot> extends EventObject { type: `xstate.snapshot.${string}`; snapshot: TSnapshot; } export interface DoneStateEvent extends EventObject { type: `xstate.done.state.${string}`; output: TOutput; } export type DelayExpr = (args: ActionArgs, params: TParams) => number; export type LogExpr = (args: ActionArgs, params: TParams) => unknown; export type SendExpr = (args: ActionArgs, params: TParams) => TSentEvent; export declare enum SpecialTargets { Parent = "#_parent", Internal = "#_internal" } export interface SendToActionOptions extends RaiseActionOptions { } export interface RaiseActionOptions { id?: string; delay?: Delay | DelayExpr; } export interface RaiseActionParams extends RaiseActionOptions { event: TEvent | SendExpr; } export interface SendToActionParams extends SendToActionOptions { event: TSentEvent | SendExpr; } export type Assigner = (args: AssignArgs, params: TParams) => Partial; export type PartialAssigner = (args: AssignArgs, params: TParams) => TContext[TKey]; export type PropertyAssigner = { [K in keyof TContext]?: PartialAssigner | TContext[K]; }; export type Mapper = (args: { context: TContext; event: TExpressionEvent; self: ActorRef, // TODO: this should be replaced with `TChildren` StateValue, string, unknown, TODO, // TMeta TODO>, TEvent, AnyEventObject>; }) => TResult; export interface TransitionDefinition extends Omit, 'target' | 'guard'> { target: ReadonlyArray> | undefined; source: StateNode; actions: readonly UnknownAction[]; reenter: boolean; guard?: UnknownGuard; eventType: EventDescriptor; toJSON: () => { target: string[] | undefined; source: string; actions: readonly UnknownAction[]; guard?: UnknownGuard; eventType: EventDescriptor; meta?: Record; }; } export type AnyTransitionDefinition = TransitionDefinition; export interface InitialTransitionDefinition extends TransitionDefinition { target: ReadonlyArray>; guard?: never; } export type TransitionDefinitionMap = { [K in EventDescriptor]: Array>>; }; export interface DelayedTransitionDefinition extends TransitionDefinition { delay: number | string | DelayExpr; } export interface StateLike { value: StateValue; context: TContext; event: EventObject; } export interface StateConfig { context: TContext; historyValue?: HistoryValue; children: Record; status: SnapshotStatus; output?: any; error?: unknown; machine?: StateMachine; } export interface ActorOptions { /** * The clock that is responsible for setting and clearing timeouts, such as * delayed events and transitions. * * @remarks * You can create your own “clock”. The clock interface is an object with two * functions/methods: * * - `setTimeout` - same arguments as `window.setTimeout(fn, timeout)` * - `clearTimeout` - same arguments as `window.clearTimeout(id)` * * By default, the native `setTimeout` and `clearTimeout` functions are used. * * For testing, XState provides `SimulatedClock`. * @see {@link Clock} * @see {@link SimulatedClock} */ clock?: Clock; /** * Specifies the logger to be used for `log(...)` actions. Defaults to the * native `console.log(...)` method. */ logger?: (...args: any[]) => void; parent?: AnyActorRef; /** The custom `id` for referencing this service. */ id?: string; /** @deprecated Use `inspect` instead. */ devTools?: never; /** The system ID to register this actor under. */ systemId?: string; /** The input data to pass to the actor. */ input?: InputFrom; /** * Initializes actor logic from a specific persisted internal state. * * @remarks * If the state is compatible with the actor logic, when the actor is started * it will be at that persisted state. Actions from machine actors will not be * re-executed, because they are assumed to have been already executed. * However, invocations will be restarted, and spawned actors will be restored * recursively. * * Can be generated with {@link Actor.getPersistedSnapshot}. * @see https://stately.ai/docs/persistence */ snapshot?: Snapshot; /** @deprecated Use `snapshot` instead. */ state?: Snapshot; /** The source actor logic. */ src?: string | AnyActorLogic; /** * A callback function or observer object which can be used to inspect actor * system updates. * * @remarks * If a callback function is provided, it can accept an inspection event * argument. The types of inspection events that can be observed include: * * - `@xstate.actor` - An actor ref has been created in the system * - `@xstate.event` - An event was sent from a source actor ref to a target * actor ref in the system * - `@xstate.snapshot` - An actor ref emitted a snapshot due to a received * event * * @example * * ```ts * import { createMachine } from 'xstate'; * * const machine = createMachine({ * // ... * }); * * const actor = createActor(machine, { * inspect: (inspectionEvent) => { * if (inspectionEvent.actorRef === actor) { * // This event is for the root actor * } * * if (inspectionEvent.type === '@xstate.actor') { * console.log(inspectionEvent.actorRef); * } * * if (inspectionEvent.type === '@xstate.event') { * console.log(inspectionEvent.sourceRef); * console.log(inspectionEvent.actorRef); * console.log(inspectionEvent.event); * } * * if (inspectionEvent.type === '@xstate.snapshot') { * console.log(inspectionEvent.actorRef); * console.log(inspectionEvent.event); * console.log(inspectionEvent.snapshot); * } * } * }); * ``` * * Alternately, an observer object (`{ next?, error?, complete? }`) can be * provided: * * @example * * ```ts * const actor = createActor(machine, { * inspect: { * next: (inspectionEvent) => { * if (inspectionEvent.actorRef === actor) { * // This event is for the root actor * } * * if (inspectionEvent.type === '@xstate.actor') { * console.log(inspectionEvent.actorRef); * } * * if (inspectionEvent.type === '@xstate.event') { * console.log(inspectionEvent.sourceRef); * console.log(inspectionEvent.actorRef); * console.log(inspectionEvent.event); * } * * if (inspectionEvent.type === '@xstate.snapshot') { * console.log(inspectionEvent.actorRef); * console.log(inspectionEvent.event); * console.log(inspectionEvent.snapshot); * } * } * } * }); * ``` */ inspect?: Observer | ((inspectionEvent: InspectionEvent) => void); } export type AnyActor = Actor; /** @deprecated Use `AnyActor` instead. */ export type AnyInterpreter = AnyActor; export type Observer = { next?: (value: T) => void; error?: (err: unknown) => void; complete?: () => void; }; export interface Subscription { unsubscribe(): void; } export interface InteropObservable { [Symbol.observable]: () => InteropSubscribable; } export interface InteropSubscribable { subscribe(observer: Observer): Subscription; } export interface Subscribable extends InteropSubscribable { subscribe(observer: Observer): Subscription; subscribe(next: (value: T) => void, error?: (error: any) => void, complete?: () => void): Subscription; } type EventDescriptorMatches = TEventType extends TNormalizedDescriptor ? true : false; export type ExtractEvent> = string extends TEvent['type'] ? TEvent : NormalizeDescriptor extends infer TNormalizedDescriptor ? TEvent extends any ? true extends EventDescriptorMatches ? TEvent : never : never : never; export interface BaseActorRef { send: (event: TEvent) => void; } export interface ActorLike extends Subscribable { send: (event: TEvent) => void; } export interface ActorRef, TEvent extends EventObject, TEmitted extends EventObject = EventObject> extends Subscribable, InteropObservable { /** The unique identifier for this actor relative to its parent. */ id: string; sessionId: string; send: (event: TEvent) => void; start: () => void; getSnapshot: () => TSnapshot; getPersistedSnapshot: () => Snapshot; stop: () => void; toJSON?: () => any; _parent?: AnyActorRef; system: AnyActorSystem; src: string | AnyActorLogic; on: (type: TType, handler: (emitted: TEmitted & (TType extends '*' ? unknown : { type: TType; })) => void) => Subscription; } export type AnyActorRef = ActorRef; export type ActorRefLike = Pick; export type UnknownActorRef = ActorRef, EventObject>; export type ActorLogicFrom = ReturnTypeOrValue extends infer R ? R extends StateMachine ? R : R extends Promise ? PromiseActorLogic : never : never; export type ActorRefFrom = ReturnTypeOrValue extends infer R ? R extends StateMachine ? ActorRef, TEvent, TEmitted> : R extends Promise ? ActorRefFrom> : R extends ActorLogic ? ActorRef : never : never; export type ActorRefFromLogic = ActorRef, EventFromLogic, EmittedFrom>; export type DevToolsAdapter = (service: AnyActor) => void; /** @deprecated Use `Actor` instead. */ export type InterpreterFrom AnyStateMachine)> = ReturnTypeOrValue extends StateMachine ? Actor, TEvent, TInput, AnyActorSystem, TEmitted>> : never; export type MachineImplementationsFrom AnyStateMachine)> = ReturnTypeOrValue extends StateMachine ? InternalMachineImplementations> : never; export interface ActorScope, TEvent extends EventObject, TSystem extends AnyActorSystem = AnyActorSystem, TEmitted extends EventObject = EventObject> { self: ActorRef; id: string; sessionId: string; logger: (...args: any[]) => void; defer: (fn: () => void) => void; emit: (event: TEmitted) => void; system: TSystem; stopChild: (child: AnyActorRef) => void; actionExecutor: ActionExecutor; } export type AnyActorScope = ActorScope; export type SnapshotStatus = 'active' | 'done' | 'error' | 'stopped'; export type Snapshot = { status: 'active'; output: undefined; error: undefined; } | { status: 'done'; output: TOutput; error: undefined; } | { status: 'error'; output: undefined; error: unknown; } | { status: 'stopped'; output: undefined; error: undefined; }; /** * Represents logic which can be used by an actor. * * @template TSnapshot - The type of the snapshot. * @template TEvent - The type of the event object. * @template TInput - The type of the input. * @template TSystem - The type of the actor system. */ export interface ActorLogic, // it's invariant because it's also part of `ActorScope["self"]["getSnapshot"]` in out TEvent extends EventObject, // it's invariant because it's also part of `ActorScope["self"]["send"]` in TInput = NonReducibleUnknown, TSystem extends AnyActorSystem = AnyActorSystem, in out TEmitted extends EventObject = EventObject> { /** The initial setup/configuration used to create the actor logic. */ config?: unknown; /** * Transition function that processes the current state and an incoming event * to produce a new state. * * @param snapshot - The current state. * @param event - The incoming event. * @param actorScope - The actor scope. * @returns The new state. */ transition: (snapshot: TSnapshot, event: TEvent, actorScope: ActorScope) => TSnapshot; /** * Called to provide the initial state of the actor. * * @param actorScope - The actor scope. * @param input - The input for the initial state. * @returns The initial state. */ getInitialSnapshot: (actorScope: ActorScope, input: TInput) => TSnapshot; /** * Called when Actor is created to restore the internal state of the actor * given a persisted state. The persisted state can be created by * `getPersistedSnapshot`. * * @param persistedState - The persisted state to restore from. * @param actorScope - The actor scope. * @returns The restored state. */ restoreSnapshot?: (persistedState: Snapshot, actorScope: ActorScope) => TSnapshot; /** * Called when the actor is started. * * @param snapshot - The starting state. * @param actorScope - The actor scope. */ start?: (snapshot: TSnapshot, actorScope: ActorScope) => void; /** * Obtains the internal state of the actor in a representation which can be be * persisted. The persisted state can be restored by `restoreSnapshot`. * * @param snapshot - The current state. * @returns The a representation of the internal state to be persisted. */ getPersistedSnapshot: (snapshot: TSnapshot, options?: unknown) => Snapshot; } export type AnyActorLogic = ActorLogic; export type UnknownActorLogic = ActorLogic; export type SnapshotFrom = ReturnTypeOrValue extends infer R ? R extends ActorRef ? TSnapshot : R extends Actor ? SnapshotFrom : R extends ActorLogic ? ReturnType : R extends ActorScope ? TSnapshot : never : never; export type EventFromLogic = TLogic extends ActorLogic ? TEvent : never; export type EmittedFrom = TLogic extends ActorLogic ? TEmitted : never; type ResolveEventType = ReturnTypeOrValue extends infer R ? R extends StateMachine ? TEvent : R extends MachineSnapshot ? TEvent : R extends ActorRef ? TEvent : never : never; export type EventFrom = never, TEvent extends EventObject = ResolveEventType> = IsNever extends true ? TEvent : ExtractEvent; export type ContextFrom = ReturnTypeOrValue extends infer R ? R extends StateMachine ? TContext : R extends MachineSnapshot ? TContext : R extends Actor ? TActorLogic extends StateMachine ? TContext : never : never : never; export type InferEvent = { [T in E['type']]: { type: T; } & Extract; }[E['type']]; export type TODO = any; export type StateValueFrom = Parameters['matches']>[0]; export type TagsFrom = Parameters['hasTag']>[0]; export interface ActorSystemInfo { actors: Record; } export type RequiredActorOptions = (undefined extends TActor['id'] ? never : 'id') | (undefined extends InputFrom ? never : 'input'); type ExtractLiteralString = T extends string ? string extends T ? never : T : never; type ToConcreteChildren = { [A in TActor as ExtractLiteralString]?: ActorRefFromLogic; }; export type ToChildren = string extends TActor['src'] ? Record : Compute & { include: { [id: string]: TActor extends any ? ActorRefFromLogic | undefined : never; }; exclude: unknown; }[undefined extends TActor['id'] ? 'include' : string extends TActor['id'] ? 'include' : 'exclude']>; export type StateSchema = { id?: string; states?: Record; type?: unknown; invoke?: unknown; on?: unknown; entry?: unknown; exit?: unknown; onDone?: unknown; after?: unknown; always?: unknown; meta?: unknown; output?: unknown; tags?: unknown; description?: unknown; }; export type StateId = (TSchema extends { id: string; } ? TSchema['id'] : TParentKey extends null ? TKey : `${TParentKey}.${TKey}`) | (TSchema['states'] extends Record ? Values<{ [K in keyof TSchema['states'] & string]: StateId; }> : never); export interface StateMachineTypes { context: MachineContext; events: EventObject; actors: ProvidedActor; actions: ParameterizedObject; guards: ParameterizedObject; delays: string; tags: string; emitted: EventObject; } /** @deprecated */ export interface ResolvedStateMachineTypes { context: TContext; events: TEvent; actors: TActor; actions: TAction; guards: TGuard; delays: TDelay; tags: TTag; emitted: TEmitted; } export type GetConcreteByKey = T & Record; type _GroupStateKeys = S extends any ? T['states'][S] extends { type: 'history'; } ? [never, never] : T extends { type: 'parallel'; } ? [S, never] : 'states' extends keyof T['states'][S] ? [S, never] : [never, S] : never; type GroupStateKeys = { nonLeaf: _GroupStateKeys[0]; leaf: _GroupStateKeys[1]; }; export type ToStateValue = T extends { states: Record; } ? IsNever extends true ? {} : GroupStateKeys['leaf'] | (IsNever['nonLeaf']> extends false ? T extends { type: 'parallel'; } ? { [K in GroupStateKeys['nonLeaf']]: ToStateValue; } : Compute['nonLeaf']]: { [StateKey in K]: ToStateValue; }; }>> : never) : {}; export interface ExecutableActionObject { type: string; info: ActionArgs; params: NonReducibleUnknown; exec: ((info: ActionArgs, params: unknown) => void) | undefined; } export interface ToExecutableAction extends ExecutableActionObject { type: T['type']; params: T['params']; exec: undefined; } export interface ExecutableSpawnAction extends ExecutableActionObject { type: 'xstate.spawnChild'; info: ActionArgs; params: { id: string; actorRef: AnyActorRef | undefined; src: string | AnyActorLogic; }; } export type SpecialExecutableAction = ExecutableSpawnAction | ExecutableRaiseAction | ExecutableSendToAction; export type ExecutableActionsFrom = T extends StateMachine ? SpecialExecutableAction | (string extends TAction['type'] ? never : ToExecutableAction) : never; export type ActionExecutor = (actionToExecute: ExecutableActionObject) => void; export type BuiltinActionResolution = [ AnyMachineSnapshot, NonReducibleUnknown, // params UnknownAction[] | undefined ]; export {};