cassiozen / useStateMachine

The <1 kb state machine hook for React
MIT License
2.38k stars 47 forks source link

[Question] How to update context without changing state? #87

Open DaveWelling opened 2 years ago

DaveWelling commented 2 years ago

Often pieces of state will be needed for decisions in the effect methods. Would you recommend keeping these instead in an external useState, or is there some way to pass these in via events (without changing state).

for instance, in xstate you can do something like this:

{
   states: {
      start: {
         on: {
            readCountChange: {
               actions: [assign((context, event)=>{ return { readsExist: event.readCount > 0}})]
            }
         }
      ...
    }
}

And then use that readsExist later in a condition to decide if some other event should be allowed to make a state change.

Johannes5 commented 2 years ago

I also want to know the answer to that.

I currently pass machine.context.baseVariant to a prop But the state machine isn't the only thing that wants to influence this prop.

It would be very convenient to be able to set machine.context.sth from anywhere. Or to make a context variable subscribe to an external variable. One-sided to either side or two-sided.

My problem is, that it needs to be two-sided.

Here are the approaches I have in mind right know for my current problem as I am writing this:

A) send("UPDATE_BASE_VARIANT") every time the variable updates directing to a state named "updatingBaseVariant" which only has a setContext effect and then sends back to the previous state. But I don't know how to programmatically detect the previous state and redirect to it :/ Luckily the state will always be the same in my particular case. And I'm also lucky that the currentBaseVariant variable will only update while the state machine is in one state. Otherwise this approach wouldn't work. This is not a clean and easy approach overall.

B) setCurrentBaseVariant() inside of some states to update the local variable that will be passed down as a prop. Just tried this while writing this message. It solves my current problem.

C) use a global state management solution instead of context Because I'm already using https://github.com/pmndrs/valtio And it is already somewhat integrated into the state machine. So I thought this would be the cleanest option, but a) context is useful in the verbose: true logging and b) I tried it and there were too many problems. While writing this I suddenly know the solution to the main problem - but I already reverted all the changes to a working implementation of B)