You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I'm using v5 and I have a question about dynamic detection of parent machines (which I can achieve, but it's a bit fiddly). I've created machineA that can be used standalone. However, machineB also uses it for specific tasks. Both machines used common utils to create state nodes etc. I would like to know what pattern the community uses to dynamically detect parent machines to say emit a final output or esclate an error when encountered. xstate will error if you call esclate when there's no parent machine, ie. standalone.
Some example code:
exportconstcreateErrorStateNode=(key: string,metaContent?: string,final: boolean=true,// < might be a reusable standalone machine?): StateNodeConfig<any,any,any,any>=>{functionconditionallyEscalateError(){// only if we have a parent machine}return{tags: ['error',key],meta: {content: metaContent ? metaContent : `${key} error.`,},entry: [setErrorByKey(`${key}-error`),conditionallyEscalateError],/** * Provide final output to parent machines. */type: final ? 'final' : 'atomic',output: ({ context })=>({error: context.error,data: context.error,}),};};
If you just always call escalate there in the entry, when standalone you'll get:
Error: Unable to send event to actor '#_parent' from machine 'machineA'.
...and that then stops/blocks the final output from completing, the complete from being called in the subscribed actor. While final is tolerant of parent or no parent, escalate and perhaps other utils are not. In my example, machineA is throwing an error to reach the above state node.
I could create a flag on a common context base type and set that via the parent when the child is invoked.
...but that seems a bit overkill. Maybe final states and other xstate utils that can interact with parent machines need to be more tolerant of missing machines rather than erroring? How do others approach this?
This works, but as you can see it's quite ugly:
exportconstcreateErrorStateNode=(key: string,metaContent?: string,final: boolean=true,): StateNodeConfig<any,any,any,any>=>{lethasParentMachine=false;letsentToParentMachine=false;return{tags: ['error',key],meta: {content: metaContent ? metaContent : `${key} error.`,},entry: [setErrorByKey(`${key}-error`),(args: ActionArgs<any,any>)=>(hasParentMachine=args.self._parent!==undefined),],always: [{guard: ()=>hasParentMachine&&!sentToParentMachine,actions: [escalateError,()=>(sentToParentMachine=true)],},],/** * Provide final output to parent machines. */type: final ? 'final' : 'atomic',output: ({ context })=>({error: context.error,data: context.error,}),};};
reacted with thumbs up emoji reacted with thumbs down emoji reacted with laugh emoji reacted with hooray emoji reacted with confused emoji reacted with heart emoji reacted with rocket emoji reacted with eyes emoji
-
I'm using v5 and I have a question about dynamic detection of parent machines (which I can achieve, but it's a bit fiddly). I've created machineA that can be used standalone. However, machineB also uses it for specific tasks. Both machines used common utils to create state nodes etc. I would like to know what pattern the community uses to dynamically detect parent machines to say emit a final output or esclate an error when encountered. xstate will error if you call
esclate
when there's no parent machine, ie. standalone.Some example code:
If you just always call
escalate
there in theentry
, when standalone you'll get:...and that then stops/blocks the final output from completing, the
complete
from being called in the subscribed actor. Whilefinal
is tolerant of parent or no parent,escalate
and perhaps other utils are not. In my example, machineA is throwing an error to reach the above state node.I could create a flag on a common context base type and set that via the parent when the child is invoked.
...but that seems a bit overkill. Maybe final states and other xstate utils that can interact with parent machines need to be more tolerant of missing machines rather than erroring? How do others approach this?
This works, but as you can see it's quite ugly:
Beta Was this translation helpful? Give feedback.
All reactions