-
Notifications
You must be signed in to change notification settings - Fork 967
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Calling a new transition from inside a lifecycle method #143
Comments
You can't transition while in a transition.
What i do is pass an object as a param, and the current transition sets a
'nextTransition' value in it, which i feed back to the state machine after
the first transition is over.
…On 9 Nov 2017 0:19, "Reuben Abraham" ***@***.***> wrote:
If I want to decide between two transitions on entering a state, I am
unable to call a transition from inside any lifecycle event. Say I have a
very simple FSM with 3 states: A, B, and C. There is a transition A->B
called step1() and another transition B->C called step2(). Say I only want
to print hello when we get to B then call step2(). How would this be
achieved? If I write an onEnterB or onAfterStep1 function, I get an error
saying that a new transition cannot be called while the old one is still in
effect.
—
You are receiving this because you are subscribed to this thread.
Reply to this email directly, view it on GitHub
<#143>, or mute
the thread
<https://github.com/notifications/unsubscribe-auth/ACE68CjEmCed4ebsAwRRypxU94Ll9cTvks5s0ikAgaJpZM4QXIcP>
.
|
Pretty much any event system will choke if you try to invoke an event within an event. The typical solution is to back out to the event loop (let the current event complete) before invoking the internal event. You can do this with either a custom event, or a timeout. A 0 length timeout is the easiest:
|
I've been doing |
Even though that the workaround will do it`s job, if before the execution of process.nextTick you go for some reason into another transition you will have a race condition and undefined state in the end. For example A(init) -> calls (B) -> process.nextTick to (C) That move to D should fail because you are already scheduled async transition to (C), but there is no way for the fsm to know this. Ideally you want to replicate the lock mechanism... |
Update 11-7-2018 Reads even cleaner with async / await const fsm = new StateMachine({
init: "init",
transitions: [
{ name: "step", from: "init", to: "dbWrite" },
{ name: "step", from: "dbWrite", to: "submitToApi" },
{ name: "step", from: "submitToApi", to: "imageUpload" },
{ name: "step", from: "imageUpload", to: "success" }
],
methods: {
onDbWrite: async () => {
await this.onDbWrite();
setTimeout(() => this.fsm.step(), 0);
},
onSubmitToApi: async () => {
await this.onSubmitTo311Api();
setTimeout(() => this.fsm.step(), 0);
},
onImageUpload: async () => {
await this.onImageUpload();
setTimeout(() => this.fsm.step(), 0);
},
onSuccess: async () => {
await this.onSuccess();
}
}
}); Got multiple state transitions working async. Could just be my ignorance but it doesn't seem like it would be too crazy to support in the library const fsm = new StateMachine({
init: "init",
transitions: [
{ name: "step", from: "init", to: "dbWrite" },
{ name: "step", from: "dbWrite", to: "submitToApi" },
{ name: "step", from: "submitToApi", to: "imageUpload" },
{ name: "step", from: "imageUpload", to: "success" }
],
methods: {
onTransition: lifecycle => this.onTransition(lifecycle),
onDbWrite: () =>
this.onDbWrite().then(() => setTimeout(() => this.fsm.step(), 0)),
onSubmitToApi: () =>
this.onSubmitToApi().then(() => setTimeout(() => this.fsm.step(), 0)),
onImageUpload: () =>
this.onImageUpload().then(() => setTimeout(() => this.fsm.step(), 0)),
onSuccess: () => this.onSuccess()
}
}); My fsm lives inside of a class with member functions that are async await or return promises. Seems like a really neat way of implementing lifecycle hooks |
Will this approach have any other effects or disadvantages? |
Hi, I could solve this problem calling the transtition inside the method writing:
If I wrote |
Maybe creator of the lib can provide an example how to make state machine which changes its state from first to last (without setTimeout) when previous transition is finished? A -> B -> C. I guess this is pretty often case. |
If I want to decide between two transitions on entering a state, I am unable to call a transition from inside any lifecycle event. Say I have a very simple FSM with 3 states: A, B, and C. There is a transition A->B called step1() and another transition B->C called step2(). Say I only want to print
hello
when we get to B then call step2(). How would this be achieved? If I write anonEnterB
oronAfterStep1
function, I get an error saying that a new transition cannot be called while the old one is still in effect.The text was updated successfully, but these errors were encountered: