# React Wednesdays: XState and JavaScript State Machines

Canonical: https://davidk.dev/talks/react-wednesdays-xstate-and-javascript-state-machines/
Video: https://www.youtube.com/watch?v=1TT2ymkYGyM
Speaker: David Khourshid (@DavidKPiano), creator of XState
Type: Livestream · Event: React Wednesdays (Kendo UI) · Year: 2020 · Duration: 1:09:05 · Views: 788 (as of 2026-10-19)
Topics: XState, State machines, React, React hooks, Statecharts

## Summary
On this episode of React Wednesdays, an epic star-studded cast talks about XState, a project helping you build state machines, and how you can use them in your application development, and why they're important to know about.

## Key takeaways (quoted from the transcript)
- Maybe you could just set the stage for us, as if for people that are joining that have no idea what state machines even are, or why you might use them, or what XState even is. (1:00)
- State machines just takes that one step further, where instead of doing an event first approach, you do a state first approach. (6:00)
- What I'm going to do is I'm going to use XState, which is the library I created for making finite state machines and statecharts. (16:00)
- If we have the logic where if we're in the saving state and we toggle again, we go to inactive, then we see that. (23:00)
- While it's an actor model, it's also like you can think of it as a very primitive state machine. (32:00)
- Cypress is a testing library, and this uses XState and state machines all over the place. (51:00)

## Chapters
- 0:00 Introduction
- 5:00 The problem is that sometimes that if statement comes after the…
- 7:00 You just put each of those in an object…
- 22:00 Clicking this button means that we are sending a toggle event…
- 24:00 We can visualize the business logic completely independent of any particular…
- 29:00 When we're in this inactive state…
- 32:00 We also had saving, and so naively you might do…
- 36:00 Typically, what I would do is I would have my logic…
- 47:00 We get that in props or alarm service…
- 57:00 By the way, I do have GitHub sponsors…
- 59:00 XState code Gen does make that a lot easier
- 1:03:00 I am personally working on XState Python
- 1:06:00 I'll throw out the newsletter again, the Enterprise React newsletter
- 1:08:00 I, I don't have this on the website yet…

## Transcript
[0:00] [MuSIC] all right, hello everybody and welcome to another episode of React Wednesdays. I am T.J. Van Tol. I work as a developer Advocate AT progress. And with me today, as always, let's go, bottom right here is Dan Wilson. Hey hey, I'm Dan Wilson. I work with digital PR mates and we do Enterprise React stuff. We also curate the Enterprise React newsletter. Which is where I found David and his great XState project that we'll talk about today.

[0:00] If it's your kind of thing, Google it, sign up, we don't sell your email address. Also with us today is Christian returning. Champion Christian Pillsbury. Hello, hello. I'm also a senior consultant at digital Primates. And, I was the one who recommended putting some XState on our newsletter. Awesome, and our special guest today is David Kay. And we just learned that the piano in your name is actually because, you actually the major Majed in piano, correct?

[1:00] Yeah, that's right. So, when I went to University, I majored in piano performance. And you could see a this way, you know, bench right there. So, yeah, very cool. So I know we want to talk about state machines today, which I'm very excited about because I feel like it's a topic that I've. I've heard about a lot, but I've never totally understood, or it's never really clicked for me. So maybe you could just set the stage for us, as if for people that are joining that have no idea what state machines even are, or why you might use them, or what XState even is.

[1:00] Maybe you could just start by setting the stage for us on all of this, all right, well, I'll actually make a really, really simple, real life example. So, you're, you could be in one of two states, either asleep or awake. You know, I, I don't know anyone who's managed to be both awake and asleep at the same time. But it's just this idea that you could only be in one of a finite number of states at a time, and also the idea that you could transition between those states.

[2:00] Like, sleeping, and you know, like when? When you're awake, you could go to sleep and then you're asleep, and then you could wake up and then you're awake, and also, uh. These finite states are special because you could only do certain things when you're in a state. For example, let's say someone told you to cook lunch or something, right? Obviously, you could only do that when you're awake, you can't do that when you're asleep.

[2:00] And so, this is a real life example, just because state machines really describe, you know, pretty much everything in real life, but they also describe the logic of our applications. Like, for example, when a button is disabled, we want to make sure that when it's in that disabled state, nothing should happen when you click it, right? And obviously there are buttons that sort of violate this rule, but, that's the general idea.

[3:00] Just there. Being a finite set of states, a finite set of events or things that you could do to that state machine. Transitions between states and other states based on those events. And so that whole collection of things just makes up what's called a finite state machine. And it's a really old concept, it's like 50 or 60 years old, if not, you know, older. Yeah, I, really like the there's a comparison to the old Walkman.

[3:00] And like, when you press the stop button, like, when can you fast forward? When can you not? If it's ejected, like if the thing is open, you can't hit. Play it actually, and the it was a good design, it actually wouldn't press down the play button, so you actually weren't all, like, physically able to do it. So it's right, yeah, and so that's. That's what's also known as a like, a mechanical automaton.

[3:00] And so what's interesting is like, this whole idea of like, like, being in only one state at a time and a machine actually doing something. A finite Aumon actually predates electronics. So, that there's like these wooden toys where you spin a thing and they dance and they do stuff. And those are known as automatons, so it's basically the same thing, and that's where finite state Automaton comes from. That's cool. So when it comes to the actual coding part of this, like, that sort of makes sense to me at a high Lev.

[4:00] But when you're actually developing, is this like a way of approaching code so that you're not just writing a? Bunch of if checks CU. Like, in my mind, it's like, Okay, I can't do anything while the button's disabled. So then, in my logic, like my brain at least, logically goes to like, oh well, then I'll just wrap this with an, if not disabled check. But I imagine this starts to get into, like, well, like, for more complex examples, right?

[4:00] You could have a lot of different state and a lot of different checks. Is that sort of where we're going with this?

[5:00] Like the these more like lots of moving pieces situation? The sort of, yeah. And that's actually a really good intuition, because when we're programming, we are already making finite state machines. We're just doing so in a very implicit way. There is the defensive programming approach, where you just litter your code with IF statements. You know, basically, making sure, you know, taking the example like, you're either asleep or awake. Like, if someone tells me to cook a meal, make sure I'm not asleep first.

[5:00] And the problem is that sometimes that if statement comes after the fact, where it's like, you know, we told David to, cook a meal while he was asleep once, and that did not go well. So we need to have that switch statement and make sure we don't make that mistake again. So eventually you graduate from IF statements to switch statements, and then you really, delineate, like what specific things can happen. And so I don't know if you're used to, like Redux or something like that, but typically you would write switch statements.

[6:00] Where based on this event, do this, based on, you know, another events do that. And state machines just takes that one step further, where instead of doing an event first approach, you do a state first approach. Be like, when David is in the awake state, here's all the things that he could do. And when he's in the asleep state, here's what he could do. Maybe he could transition to the awake state, you know, and so on, and so forth.

[6:00] So, also, you don't need a library to implement this. If you search state machine in virtually any language, you're going to see patterns similar to a switch statement, or whatever other language. Constructs you know are provided by that. Language that allow you to implement state machines, it's essentially a data structure. It's nothing special. So well, I know you wanted to show some of this off, so maybe we could switch over to you showing some of this.

[6:00] Because that might help make this, a little bit more concrete.

[7:00] Yeah, I have a feeling most of the audience are kind of thinking, Okay, great state machines. How does it change what I've already done? Sure, so I could go ahead and, just make sure I have the right screen here. All right, there we go. So, yep, the audience should be seeing it now. So I. I have a very, very simple example. And honestly, this is something that you would typically just jump straight into you state for.

[7:00] Let's say I have an alarm app and I want to turn an alarm off and on. First of all, just to show you how this works. I have a data state equals inactive active, and this is our first clue that, you know, we're dealing with finite states. But right now we're not doing anything special. We're just, you know, switching back and forth between inactive and active. So let's say that the business requirement here is I want this button to toggle this alarm on and off, right?

[7:00] So we could say const, this is just the way you would normally do it. So, toggled, set, toggled, or you know what is active? A lot of people love using these Boolean flags, like the is, whatever, so I'll just, Oh man, I use them like crazy. Yeah, you'll. You'll soon realize that, like, if you have more than two states, it's not really sufficient. And I'll I'll demonstrate that here too. So we could useState false, right?

[8:00] And then over here, we could say, say, is active. If I make a mistake, it's because my hands are freezing, because it's actually cold. In Florida, it's like 40 degrees Fahrenheit, which is, I mean, this is what kills Floridians, just almost freezing temperatures. It's terrible. So my hands are still thawing. Christian and I are both Floridians and so we agree with you. Well, Chicago, though, so I don't agree with you anymore.

[8:00] But I, I remember, remember your pain. And TJ is from Michigan, so he thinks of. 40 degrees is a nice, balmy summer day. You know, I was actually I. I was actually born in Chicago, so I should be used to this. But I moved when I was eight and I haven't been back. I, I only been back once or twice since. But yeah, okay, so our alarm app is working. You might think, all right, this is sufficient.

[9:00] This is all I need, just a simple little use date and a toggle over here. And, as I said, this is, suff, sufficient when you have two states right off or on, but not everything is like that. Let's say that we had this alarm app connected to many, you know, IOT devices or something like that, and we want to save this to the cloud. So now we have three states. And I've seen people doing terrible stuff, like, you know, treating true, false and null as like a triple Boolean, which this is a crime.

[9:00] You should be arrested for this. But boxes in design. So, let's say that we want to have a way to. You know, have some sort of pending state, where it's like saving to, saving to the cloud, and I, I already have a data state equals saving in the Styles. So, so we have to refactor this. And so instead of, having true or false, we could have inactive, so we could say that this is either inactive or it's saving, or it's active.

[10:00] So now we have three possible states that we could have this, and so we could say that this is instead status right, effectively an ad hoc enumeration of the possible states. Exactly, yeah, if you're using TypeScript, this becomes easy, otherwise you could have, like con states, equal, like inactive, inactive, but, you know, that becomes fair. VEROs so we're just going to have it as strings. But you could. Implement those enes however you want.

[11:00] And so, let's say set is active to saving once we click it. Or, you know, we have to do this. And this is what, TJ you were talking about at the beginning. Using if you know, else if statements. So we have to say if, status is not equal to, or, you know, if status is equal to inactive, then we want to. Set is active to saving, right? Yeah, you got to guard that exactly.

[11:00] So, right now it's inactive. When we click it, you know, Fades out. And so now. Typically, what we would do is, you know, we would, have some sort of API call and then manually set it back to active. So I'm just going to put a useEffect in here to do that. And we are going to, let's, let's just fake this with a set time out, so we're going to say, set, oops, don't unmount while you're, yep, we have to remember our unmount and all of that.

[12:00] And actually, if you could bump up the font size like one notch, that would be helpful. All right, are people complaining in the chat? Oh, no, REM. Bring your monitors closer to you. My adjust my glasses here. Okay, no worries. So, but we're gonna set the status to active after H. One second should be enough and of course, we need to have our cleanup. And this is. This is honestly really, annoying to do it like I, I've done this a million times, so I just, it's that.

[12:00] And then clear timeout I and, yeah, oh, we have to do this, uh. If our status changes, so basically, if the status is not equal to saving, then return. So now we have two areas where we're having this defensive programming. All of this if statements right, if status equals this, if status equals that, and so it. It becomes really difficult to, you know, to clearly show where the logic is. And so I'm going to say over here, else.

[13:00] Set status inactive, so click here. After a while it goes active, and then I could click to make it inactive again, and then I click here, it goes active. Now. Let me ask, you can you see immediately? Can you see any sort of bugs with this? I mean it, it works, right, but is there one bug that, you know, might bite you in the butt? Later, Christian's compiling I. I will say that about 40% of the code that was on the screen was related to conditional booleans.

[13:00] For for states, right? That's kind of annoying, because when you go back through to try to figure out why, something's breaking. You now have to parse all these bullion and hold all this stuff in your head. To try to figure out where the false condition is, or where some where the action is that you don't want. And it just seems clunky. Although I'll confess to having written many IF statements in my life that probably shouldn't have been there, right?

[14:00] And and so the, the way developers would look at this would be like, you know what? Yes, the IF statements are annoying. I'm doing a lot of defensive programming, I'm not sure of any better patterns, but this works. So it. You know, the typical wisdom in programming is, if something works, don't touch it, just leave it alone. It just works, you know? Also, it feels like, I mean, if those are the, you could also excuse it by saying, well, these are the requirements, right?

[14:00] Like, I have these things, so of course I need if checks, because this is just the way it has to work. Sort of thing. At least I might approach it that way, possibly. I think people do write code the way that they think, not the way that they read. And so they've optimized for how it is in their head. Not not so much how you might try to, like, gather the context from reading code you didn't write, right?

[15:00] Yeah, so, honestly, all of our business, you know, logic, use cases, whatever they're covered in here. But I'm going to show you a bug that really only happens. If you've either run into this issue like a hundred times before, or if you, one of your users inevitably runs into this Isue. So I'm going to turn the alarm on, but I'm like, you know what, never mind, let's turn it off. Yeah, oh, it actually did clear the timeout, so, if you're, you know, if you're not careful about, like, clearing this timeout, then you might get this race condition.

[15:00] Where it actually or actually should set it to active. I guess I have to save it to do that, okay, so if I, you know what? Oh see, do you see what happened there? It was saving, and then it toggled again, and then it toggled to active already. And you know, obviously you could fix this. By doing that, so saying, you know, if this STUS is not equal saving, it's going to clear that timeout.

[16:00] But that's that's really indirect logic. It's not really clear that, you know, we could naturally prevent that from happening. So let's jump into actually using a, state machine. And I just want to mention that doing this con status set status. This is a really good first step to, um. Just using the idea of a finite state machine in your application. But as we saw, our transitions aren't explicit, but our states are explicit, so you have an invigoration of possible states.

[16:00] In fact, exactly. So, uh. What I'm going to do is I'm going to use XState, which is the library I created for making finite state machines and statecharts. Regardless of framework. So it doesn't really matter, if you use this with XState or view, or spelt, or Angular, it's just going to work. So I'm going to create, create a, let's call a alarm machine, and this is going to be create machine. And so what you give this is, it's basically a JSON object, you give it an initial state, so let's call this inactive, and we've already gone through our states here.

[17:00] So you just put each of those in an object, so we have inactive, saving and active. And so, one good pattern over here. You would typically move from used state to useReducer and actually make each of these explicit events or dispatching explicit events instead of, manually changing the state. Because then we get to problems, or we avoid problems, like, you know, we just saw there and so, the way that we could do transitions is we say on.

[17:00] And so it sort of reads just like a normal English sentence where you say, on toggle, go to saving, oops, Exra coing over there. And then when we're in the active states, on toggle, go to inactive. And so we could say the same thing here. So if we're saving and we toggle, then we want the logic here to, to go to back to inactive. Of course, we could remove this and be like, you're not allowed to touch the button while it's saving.

[18:00] But you know, that's up to your, you know, business. Logic so, and real quick, what is toggle called here? Is that like an event? Or, yes, so that would, that would be an event? And yeah, actually. It might be good to just, visualize this for you, so if I go to XState this, which, here we go. T.h. This is an older visualizer. By the way, I'm working on updating it, but if I were to just paste this machine in here and click update.

[19:00] Now, we clearly see how each state could move between each other. So we have saving. And so if I wanted to say, you know what? Let's make a saved events and that should go to active and we update. Now we could see that the way to get to active, we toggle, have the save event occurred, and then, you know, we could go back to it being inactive. And so that's a visual representation of, you know, our machine.

[19:00] If you look at TJ, he's gonna try to pasting in his many if statements into this visualize, try to get the same response. Can he fork that code? Can you change it? Oh yeah, so, you could log in updated. What it does is it saves to, to gists, so you would log in with your GitHub account and the only thing this visualizer does is I request, read write access to Gists. And then it just saves for you.

[20:00] So, yeah, so with this visualizer, you can kind of walk through your states and how to get there. That's outside of the code perspective and even outside of the application perspective. So you can make sure that your chains or your changes in state all make sense. And then you can put that back in your application without having to once again use the application to test the states. Right? Yeah, but so, like I said, this was the old visualizer and the going back and forth between the visualizer.

[20:00] It's extremely useful, but after a while it gets annoying because you're doing a lot of copy and pasting. So I'm gonna actually show you a really cool solution for that. Pretty soon, but let's get rid of all this code first. So I'm going to say, const, oops, const. State send equals use. Machine and so this used machine hook comes from XState React. And, if you know how to use, useReducer, I hate that they start with use.

[21:00] If you know how to, you know, put in useReducer in your applications, then used machine is going to feel very familiar. You could think of a machine as a superpowered reducer, by the way, that handles side effects and all sorts of stuff, but it's essentially the same thing. If nothing else, it's just an awesome API name like useMachine, just, I mean, it just sounds really cool. Yeah, yeah, it's a slightly different paradig because of the way the imperative, the relation between the imperative and the functional works, but it's a good reference point, definitely.

[21:00] Yeah, so let me just show you what this, what this date looks like. So when we useMachine, we are going to get a state object, and, sorry, the font is a little smaller than what's over here. But the important part is, you get like this value of inactive and you also get the event that just happen.

[22:00] But the important thing is that value and the context. If we're actually dealing with external data and not just or extended data, and not just finite states. But if we actually use this in here, then instead of doing this Boolean logic, like, if else, all that sort of stuff, we could just say that. Clicking this button means that we are sending a toggle event corre you could also send a type toggle object.

[22:00] But if it, if it doesn't have any payload, then I don't know. I like being lazy and just sending a string. Shand it, yeah, so let's see what this does. When we click this, it will go to the saved state. And I'm just going to simulate like a 1 second, going to active over here, I'm just going to say app after th000 milliseconds, go to active. Just for a demonstration purposes. And I have to put that colon over there.

[23:00] So now I click here and then it goes to active. Then notice what happened in the active state. The exact same toggle events, you know, moved to me back to the inactive state. And so you could see over here that there's a whole lot. Of nothing. And that's because all of the logic is over here in our machine, we don't need this anymore. This send toggle can be called, you know, pretty much anywhere where you know this, where you have access to this send.

[23:00] And if we have the logic where if we're in the saving state and we toggle again, we go to inactive, then we see that. You know, it's not going to do that, you know, mistake where it goes to active, right? And and you've also completely decoupled your business bus logic from being deeply tied to the code.

[24:00] That's just about React. So you were mentioning before, well, first we were looking at a visualizer. Guess what? We can visualize the business logic completely independent of any particular application or view implementation. But also you were pointing out that you can use, XState with View or Angular or whatever. And now this code has nothing specific to do with React and React hooks, other than the fact that's where you're telling things to, like, send the particular action.

[24:00] So there's a lot of value of, like, having it defined completely independent, and it's also completely serializable, because, as you pointed out, that it can, it's basically. JSON. Yeah, yeah, and those are really good points. And when I tell developers that they think, you know, that's cool, it's like, sort of the same thing as saying, like, Oh, you could, you know, do time travel debugging? Or you, you know, your functions are pure and whatever.

[24:00] It's like, those sound cool, those are good buzzword. But what benefit does having my entire business logic externalized actually give me when the way I was programming before works just fine? Or at least for the most part, you know, save those few edge cases. And so, just to demonstrate, let's say that I import, I have an inspect here from XState inspect, and this is something that I created a couple months ago.

[25:00] It's an inspector utility that allows you to visualize a machine in real time as you're running your app. And so the way that this works, I'm just going to call inspect. With iframe false by default, it looks for an iframe, and it puts the state machine directly into the iframe. And then I have to set. That tools to true. And the reason you do this is because obviously you don't want this running in a production environment.

[25:00] But once I [Music] save, what it does is it opens up. This visualizer, that shows you. You know, let me just try to put this side by side. So if I put this here, I put that here. It's a really tiny alarm, but here's the visualizer, and this machine shows what's happening in the application as we're playing with it. Super holy crap. I'm so glad you built that, thanks. So, you know, we could go here and we could see, okay, that's happening.

[26:00] We have a record of all of the events that are happening here, which I mean, they're pretty simple, and a sequence diagram of the events too. This is useful for more advanced use cases, where if you're invoking or spawning different machines, then you would see them sending events to each other. But also we could control the app directly with this as well. So we could, you know, toggle this back and forth.

[26:00] And that's one of the beauties of completely externalized your application. Logic is just the ability to do that. This is blowing my mind a little bit that I didn't realize that was there, and that's really awesome. Tech technical question is the events tied to the your history configuration on the machine, or is it independent of that? What do you mean? So you can specify how long of a history you want your machine to maintain.

[27:00] Is the inspector? Oh so, right now it's a little bit naive. You know, I need to take the time to actually make, you know, settings and things like that. But, right now, it just keeps the history of everything. So you, you know, you should be careful about, you know, using the inspector, at least until I update it. And for people who are already using the inspector and have been for a while.

[27:00] It's mainly the same as a couple months ago. Which is because right now I'm working on an XState creator, which allows you to, visually design. State machine Maches, you know, using your mouse or drag and drop tools or whatever. And so everything from there is going to affect. This inspector as well. So you're going to have a lot of updated visuals and a lot more cool things. So, one day, yeah, I, I will get around to, I was just CU, yeah, adding settings for that.

[28:00] So, so, one question I have is, so, looking at the state machine, like the fact that it's all just one JSON object. Like, I'm curious how? Like, in my head, I'm thinking, well, at some point I'm going to need some custom JavaScript code to run. When these states change. Do I like, is there a way like I could subscribe to events? Or I'm even thinking, like, so you have in JSON there the like after 1000?

[28:00] Do it like? If that were an actual needed to do, like a fetch call to a server or something, what would that like, sort of look like? And I don't need to like Cod out the whole thing. I'm just curious at, like, a high level, what that would, sort of look like. Because I'm having a hard time thinking through that in my head.

[29:00] Oh, why not, you know, it actually doesn't take too much. So, we this is where we get into invoking, you know, different machines or different actors. And it. This is actually very much based on the actor model. So if you're familiar with the actor model, which is also really old, I, I just like, really old, you know, computer science concepts, uh. But this is going to make a lot of sense. So instead of this after 1000, let's say that we have a cons save to server or something.

[29:00] And so this is just going to be a function that makes a new promise. Again. We're going to do that fake, you know, just after one second, we're going to say that. So set timeout and we're going to just resolve I guess with nothing and do thats. Yeah. So, the way you would do that here is, you would invoke the actor and so that just works like invoke source. And then, it takes the context and the events.

[30:00] But we're not using those at all. Otherwise, this session would be like much longer. So we're just going to save to server over there, and so this is our custom JavaScript. That eventually, you know, returns a value, so we could say, onone, that goes to active. We don't need that saved anymore, so we're going to save that pause. After one second, it goes back here and you know what, let's do our race condition.

[30:00] So if I click here and then go back, nothing happens. And you might be thinking, like, Oh, did you clean up the? Nope? I didn't do any of that. I, I purposefully just made this at timeout run and didn't worry about cleaning it up or anything. Because what's happening is this undone is a special event, and, just like any other event, the way that state machines work is just events. So when we're in this inactive state, if we get that special undone here, we're not handling that event.

[31:00] So the state machine is going to be like, I'm not doing anything with that, I'm G to stay in my state and, you know, everything is going to work just fine. But, of course, you could also, useEffect and subscribe to the state here, and it also, returns what's called a service, so you could useEffect, service. subscribe. And, that gives you the state, so console..log state, and then over there you could run whatever JavaScript you want.

[31:00] I see, so if you like, even if you wanted to, just you probably could put your switch in there. Then if you still needed it. For doing something very specific, or something that wouldn't fit logically in the JSON up there, exactly, yeah, and it's there's like a lot of well-defined things.

[32:00] So, for example, XState also has things like on transition, so you can hook into particular transitions. If you particular transitions. There's a lot you can do. Because it conforms to the very old, well trodden specification. I actually really like, David, you're, you have a really good explanation. I don't remember if it's in your docs or where, but on thinking about how promise? While it's an actor model, it's also like you can think of it as a very primitive state machine.

[32:00] Yeah, there's the state of it's doing the promise E thing, and then either it is done doing the promise thing, AKA it resolved, or it has failed to. Do the promiseiAMCPcommand implementation of promises? This is promise j..org. I think that's like the most official promise thing, or actually, no, it's. It's, you know, originally an answer on Stack Overflow, but it describes the promise as a state machine, and that's exactly what it is.

[33:00] So, but yeah, as you mentioned before, too, uh. There's a spec called statechart XML, which was, you know, published in 2015, and this is a whole bunch of XML stuff. But I just want to say that XState doesn't really invent anything. It is based on this spec and it tries to adhere to it as closely as possible. So it's not just a fancy state library where, you know, I add features on my whim.

[33:00] No, it all has to be based on this spec. I did have one more question on the code. If you go up to that invoke block up, there is what is the is the trigger for that? Just anytime the state gets changed to saving, it just knows to do the invoke part of it automatically. Yes, so once you're in the saving, this invoke is going to run for the lifetime of the state.

[34:00] So if you leave this Savings state, then it gets cleared out or it gets stopped, whatever is being invoked over there, okay, so we talked a little bit about complex Boolean logic and if statements and whatnot, like, what? What kind of guidance would you give, knowing that it's a very slippery slope? To just add one more if statement at what point should a responsible developer quit adding IF statements and begin implementing the state machine concept?

[34:00] Well, personally, you know, back when I was, you know, first learning about state machines, when I was doing app logic. And I, I admittedly did use a lot of, you know, if statements and whatever. Eventually, you get these really, really gnarly if statements where you're doing like if this and not this? And you know this and this and not this. And like, just huge statements where you know, you don't exactly know what's going on.

[35:00] The number one tool that I would use is just pencil and paper. You would say, Okay, you know what? Let's actually outline what are the states that my app can be in, uh? And typically that happens when you have more than two states. So you see how, like our alarm over here we had con is active, set is active, equals useState false, right? But we also had saving, and so naively you might do, is saving, and then we have set is saving.

[35:00] And so you're doing this because you're trying to figure out, is it in the active state, is it in the inactive state, or is it saving? So you have a total of three states, however, over here, you have 2 * 2 = 4 possible states, which means one of those states is probably wrong. And that would be like if you have active and Y, and so that would be an example of an impossible state.

[36:00] And I actually see this all the time.

[36:00] Where you have is loading, is success, is error, and you could potentially have is success and is error at the same time, or even is success and is loading. And you might think, you know, Oh, that's silly, why would anyone ever have? Is success true and is loading true? But I've seen web applications where the data is definitely loaded, but that loading spinner is still there, doing its thing. And you're like, why?

[36:00] And it's probably because they don't have, you know, robust logic to remove those impossible states. Yeah, another. Another good rule of th that I think should be applied is, if you can't, if related logic, that's dependent on one another. For the business rules or the behavior, or the app, logic is like dispersed and defuse in the codebase. So in your original example, you had business logic that was in your useEffect, but then you also had a business rule that had to be defined in your.

[37:00] Your Onclick handler and so, but that Onclick handler had better be working the way it's supposed to, even though they're like, not close to each other. And as your app is getting more and more complex, then it's going to be like, well, I don't even have a central location. That's telling me how this stuff is supposed to work. Whereas a state machine very clearly articulates and interrelates all of the moving pieces of them.

[37:00] Yeah, yeah. Typically, I see developers shove a lot of business logic in their event handlers. And honestly, if you think about real world devices, like a calculator, for instance, do you think that? The equals button or the plus button has like a microchip computer inside that little button that does all the possible? Logic no, like all that button is doing is sending a signal to, like, some sort of internal motherboard. Like some central place, and you know, it's, that central place is what's doing the logic.

[38:00] And that allows you to be really flexible with when you call events and how you call events. I, I want to show one quick other thing. Not over here, but just as an example, like I, I recreated the Android, you know, timer, with XState, and so this is also using a state machine as well. And the thing is, this is completely framework independent, and I wanted to see, like, can we actually get this running, you know, in some other framework?

[38:00] So what I did was I copy and pasted that machine and then I put it in View, and so this works pretty much exactly the same way. And in fact, because it's the same machine, you, you're guaranteed that it is going to work, the same as the other machine. So we have the same timer machine here, absolutely nothing to do with View. And then once you go in your app, you see all you have are these send calls.

[39:00] And so when you reduce your app logic to just states and events that are sent from whatever, then, the machine is sort of the brain of the components or the application, and, you know, everything is reduced to just send events. So your view code is just reviewing and your business logic is just for business loging, and things are where they're supposed to be. Yeah, and kind of related to that. I'm wondering, I think a harder question in my head is, when do you think for?

[39:00] Uh? You know? Redux is kind of waning in the background, but useReducer is replacing it, or you might be using Recoil if you need a more fragmented Global state. So I guess for me, the question is, when do you think XState is appropriate? when do you think it's actually not appropriate? Because that's another. Way that you can still centralize your business logic. You're using actions instead of you're Eventing on Xtape. But you could, like you were saying earlier, it's an inversion of a relationship, so I'm assuming it has to do with that relationship.

[40:00] So, yeah, I don't know what do you think, right? Well, I would say, like, when you're working on an application, if it's extremely simple, the US state hook is, you know, great for just simple state. If you know exactly, what you're doing, and you know that, the logic's going to be really simple, uh. But then after that you would graduate to useReducer, and that is something that I would definitely encourage. First, just this power combination of useReducer and useEffect.

[40:00] And, uh. Typically, what I would do is I would have my logic and useReducer, and then I would have useEffect. Based on the state of, you know, whatever comes from useReducer executing my effects. But even that could feel a little bit implicit. So, after that, once you're reducers and useReducer become really complicated, then I would say move to useMachine and XState. Because, honestly, the API is exactly the same, say for this service, but instead of states S, you would have state dispatch, and otherwise it's exactly the same.

[41:00] Also, talking about Redux and Recoil. The thing with Redux is it's a single Global atomic store, which honestly, that's one of the things where Redux, initially touted that as a benefit. Where, okay, you know you? If you have many reducers, you combine them all into one single reducer and they all get the same event. But they most of the reducers re ignore the event that they don't care about. But XState is more decentralized, it's, it's an actor model.

[42:00] So each machine is, you know, just localized to, each of their components. Or you could pass it down through context if you want. But yeah, so you have that, and also, recoil, recoil, and libraries like that are still very manipulate the states. I, I almost want say imperatively, and it pretty much is imperative. Recoil allows you to do that decentralization that I was talking about in an actor model like fashion. However, your logic is still not very clear.

[42:00] You're not sending events, you are literally changing the state whenever you want. And Recoil is just doing this magic in order to make sure that's, propagated to the components that care about that state. And that's fine if you're doing things like, like, I don't know, drag drop applications or applications where you have state. That needs to be read by so many different things, and there's not any complex, transitional logic going on.

[43:00] But yeah, I. I would say treat XState like useReducer in a distributed fashion, not in an atomic Global store fashion like Redux, but in a distributed fashion. Just like Recoil. You know, I can see a number of people wanting to give this a try, but they may face some resistance. You' had some questions stack up here in the chat, let's let TJ get to those, and then I want to get your thoughts on how to sell this internally.

[43:00] Okay, yeah, because we, first of all, you've got some fans of XState in the chat. We got some people that really like XState. And then, oh man, I. It's a tradition here on the show that I always fail at pronouncing Twitch names. This looks like L1 not I got L, not L. Not okay, we'll go with L, not. But big fan of XState wants to introduce that in their company. And in the meantime, they've been using useEffect reducer.

[44:00] For a couple of features. And wants to know is there any way of implementing the useEffect reducer with an API that's more like the XState one? All right, that's a great question. I actually don't really promote useEffect reducer too much just because I'm lazy, but I. I created useEffect reducer because a lot of people are, you know, doing this dance between useReducer and useEffect. And they, they're finding limitations with it, like you again, you have to do a lot of defensive logic to make sure that your effects run at exactly the same time.

[44:00] And I just wanted to give it more of an imperative, interface, where, inside your reducer. And this is going to look like Blas for me, by the way, Zo, but uh. You get your state, you get your events, by the way they call it action. This was a huge mistake by Redux. It's not an action, it's an event, or a signal, or a message. Just an action is something that's done like a side effect.

[45:00] So I use event wherever I can, instead of action, it's an event. And also you get exec, and so this exact allows you to, you know, as the name implies, execute side effects. So over here, I'm just executing this console.log going up, and I'm also incrementing the count. So this works just like a normal red producer, except with that exec as well, and so this allows you to, be very precise about when your side effects are executed.

[45:00] Now I know what you're thinking, is this reducer pure? Yes, it is still pure. Because internally, this effect or this exec doesn't actually execute this. Instead, it puts it in an array and then useEffect internally reads that array and says, Oh, here's something I need to execute. And this is basically something that you would already be doing with useEffect and useReducer. It's just combining the two in there. And so this I.

[46:00] I actually created. useEffect reducer as a stepping stone to use XState. Because, exec is the same as an action. And your reducer state is the, you know, would be the same as what you would define in a statechart. With, with XState and with XState, React so well, there you go. L, not, you're half there, yep. Also, L says they take pride on using useEffect reducer and not useEffect at all as well.

[46:00] I, I really should promote this more. It's, it's a tiny library, it's, you know, it doesn't really do anything too crazy. The TypeScript might be a bit scary, but that's because I'm using TypeScript, uh. And it should be concurrent mode safe, I say should be, because no one ever really knows for sure whether they're comp. Yeah, another question that came in from, Oh man, here we go, here we go. Dan uh.

[46:00] Solo UARS 89 A.A.R. 89.

[47:00] Yeah, we need more John do and Jane do's to watch React Wednesdays. But, they want to know. How would you share a state machine? Between two components. So, sharing a same machine between two components is the same as, like, sharing, I don't know, basically anything else subscribable, between two components. So, useMachine does return the service over here, and this service is an object that you know again. You could call on transition, you could call subscribe to, you could do whatever you want with that.

[47:00] In fact, let's say that, you know, I put this machine in the app instead, and I set the alarm Ser oops, Ser this to service. I'm usually better at typing, but it's freezing over here. I the worst at it, so you're doing great. So we get that in props or alarm service, and then there's another hook called Dat send equals use service, alarm service, so use service is for an existing machine.

[48:00] And then I'm going to save. Oh wait, no, did I do it right? Oh wait, wait. Yeah, service, I don't know. It's supposed to work. What we made before, folks remember, it takes. Oh wait, it does work. I was gonna say it work, like it definitely should work. So that service you could think of as an actor, which you could basically pass to anything. So right now, I'm passing it directly to this component.

[48:00] Or I could, I could use. Use context and just to show you that it's it is being shared. All of these are, you know, using the same instance of the service, so basically simple as that, use context or pass it in directly. That's how you share a machine, so that's one machine shared across multiple components. I imagine, like in a real world app. It's probably reasonable to have multiple state machines as well, right?

[49:00] Because there's probably, like, I could see there being like an app state, but then a state for some other process, right? Especially if you like, have like a dashboard like situation where you have lots going on. Would it be reasonable for multiple machines even to coexist? Yeah, definitely, definitely would. And in fact, that's what I do already, in the in the inspector, all of this stuff. This is actually a React app, it's a Next..js app, and I'm using all sorts of different state machines.

[49:00] Like, you know, this panning. Behavior, different state, machine, for, you know, just controlling the events and sequence and state, and even, you know, just all of that. So, yeah, you would, yeah. I think the question that TJ is getting at is from the architectural perspective, like, where does one state machine begin and end? and where should another one begin and end? Well, that's honestly up to you, I. I like architecturing, architecting my apps from a data first, you know, perspective.

[50:00] Basically, I want to ask, what data do I need, what things can happen to that data and structure it that way? And then I build my user interfaces around that. So I am using a lot of used service, used machine, only when I know that the machine is for that component only. But yeah, it's basically the same answer. As if you were designing something with Redux, like, how do you organize your app?

[50:00] Logic so that ST is shared, you know, amongst many components, right? Yeah, I think going back to the point before, it's, what is actually related to itself? So so that doesn't fully answer the question. But like, if you need states that have to do with something that is not at all the alarm, then that probably doesn't belong in your alarm machine. Because there isn't an inner relationship between states and transitions for those states.

[51:00] So you wouldn't want those to live in the same state machine, you'd want them in a separate one. So so a state machine is kind of centralized around a concept in your application, a named concept, and drives that concept forward. And as long as going back to TJ's dashboard example, if you had 15 charts, they could share a copy of the state machine. Since, you know, if you have chart view, table view, that's pretty straightforward.

[51:00] But if you had different charts that didn't have the same behavior, they would require different state machines. Right? And I encourage. There's this real world app built by the Cypress team. Cypress is a testing library, and this uses XState and state machines all over the place. So if you want to see how a real world app works with state machines, this is a great repository to do so from. And it's on.

[52:00] GitHub. So just the kind of question that I that I think people might have and maybe not know that they have is. If they come back to their co-workers and say, yeah, yeah, XState, it's the exact thing that we need. They're going to run into the typical resistance that new ideas get, where someone doesn't understand it, so they kind of shoot it down. Like, what are the common objections that you hear when somebody wants to begin implementing XState, and what might someone say to help overcome those or broaden the conversation?

[52:00] Well, a lot of the things is like, first of all, XState, you know? With state machines and statecharts, you have a learning curve, but unlike libraries where you have a learning curve learning the library. This isn't so much a learning curve for the library. It's more of learning curve for learning the principles behind state machines and statecharts. And even the actor model, and those are really useful things to learn, even if you don't use XState at all.

[53:00] So, that's definitely one of the objections. Just, you know, learning the stuff. And that's why, you know, when I first introdu this, like the very first time, it went from like seven GitHub stars to nine GitHub stars over the course of two years. And I'm like, okay, people really aren't interested in this. But once I, you know, showed the benefits, then, you know, it got a little bit more popular. And people actually started realizing, you know what?

[53:00] Fine, I'm just going to sit down, take an hour or two and actually learn what state machines are, what statecharts are. And then once you do, it's sort of this effect where you realize, okay, pretty much everything is a state machine. And I could describe so much app logic using these ideas. So, that's why, like, you just going back to the question, just convincing your co-workers to use this? I would not convince them to be like, Hey, check out this XD library, go do this.

[53:00] I would more be like, you know what can we try describing our logic using boxes and arrows? And then once I do that and my co-workers do that, they, you know, they start thinking like, Hey, this is a really clear. Way to, to describe our app logic, everything makes sense, you just follow the arrow, it's all very visual. And then you transition from that to being like, are there libraries that actually do this?

[54:00] And actually, there is one that we haven't KN like a whole lot, and it's free. So I think the message of the actor pattern is you get to encapsulate all the way up to the message level. And everything else sort of responds to that message the way it's configured to. So there's not a lot of leakage or things poking other things or causing side effects. Those are generally considered good programming practices.

[54:00] Right? Point about the kind of crazy if statements and conditional booleans is a good one. I don't know who likes to read that stuff, but it certainly as easy to write. And so, like, what sort of effort would it be? And I know this is going to be the it depends answer, but try to color it in if you can. Suppose someone has a reasonably complex application not using these principles, like, is it a small undertaking, a medium undertaking?

[55:00] Is it like a crazy undertaking to get towards this model. That, yeah, that's a good question, where it definitely does depend. But, I, I like, XState and just dat machines in general, being a refactor target. And that's because, you know, typically we build our logic from the ground up. Might not be the best idea, but it is the quickest idea for just getting that code in there and making the app work.

[55:00] MVP. There might be bugs, whatever it works, and then from there, that's when you would start, like, first, just like containerizing your or not containerizing. But like just encapsulating your logic into, like, only the logic that deals with the alarm service. We're going to group it into this and group other logic into other things, really understand how the logic works in terms of states and events, and then convert each of those to a machine one by one.

[56:00] And so that's why, with use, machine, use, service, all that. You're basically converting reducers that you would have written anyway into a machine, and that's why I say machines are just reducers with rules, right? So yeah. And part of that, so the point of it being like it doesn't have to happen all at once. It can be iterative and you can prioritize it in whatever makes sense for your project plan and everything.

[56:00] But on top of that, I think one of the hurdles, especially as your app becomes more and more complex, is one of the reasons to favor using XState. In the first place. As we were talking about earlier, with all, not just if statements and complex if statements. But your business logic is strewn about, and it's almost definitely not documented by a technical business analyst. And so when you're saying now we need to migrate this to something that's clear and coherent, it's like, well, I don't even know what the business logic is.

[56:00] Because it's in our hundreds of thousands of line codebase, it's in like 15 800 places, right?

[57:00] Not even have like edge cases that we haven't seen yet, right? Exactly, no, that's a very good point. And I, you know, as we look at the pre-code here and the postcode, you can certainly see. There's less room for weird errors to leak into production and cause that whole expensive workflow. And we've had a couple fun things come in through chat as well. Like line said, that did exactly that, just taking like pencil and paper and drawing out the state to show co-workers and even product owners.

[57:00] And also recommends Escala draw, which is a fun little tool for drawing some of this stuff. And there's a couple other, I think. One last good question also Dan you, you, apparently got this name correctly, so congrats on that. But I thought this question might be a good one to wrap up on because we're coming up towards the end of our time. Lat's also curious, what are you expecting? What other tools can we expect in the following months?

[57:00] What are you working on? And I'd also maybe add on to this. For people that are new to X8, is there like a recommended spot you have for getting started as well? Is it just the documentation or anything you think people should read? Sure, so I'll answer the tools question first. So, it's me and a couple other contributors just working on next Dat. Obviously I have a full-time job. So I'm really only able to work on this on, you know, just after work.

[58:00] And, by the way, I do have GitHub sponsors, which I'm extremely thankful for, because that's that's really just something that pushes me to keep going. And so when I see, like, Oh, there are sponsors who are actually really, thankful for my work, then you know, I. I just spend an extra hour or two each night and work on this. Not not having kids helps, but so a lot of the things that I'm working on.

[58:00] We are working on a version five live of XState and don't be scared, the API is going to be pretty much the same here.

[59:00] There are going to be a couple changes like to invoke and things like that, but a lot of XState. Version 5 is, just making full compatibility with, SCXML, the spec, and also, making it smaller, making it faster. You know the typical things that you would expect in a major release with, you know, very few breaking changes, but you know, if there are breaking changes, then that does merits a, major release. So working on that, working on more visualization tools, like the thing that I mentioned, a drag drop editor.

[59:00] It's going to be called XState creator, and it's going to be a way for you to create XState machines. Visually, instead of doing so in code, even though doing so in code isn't really that hard. There's other projects too, like Xade code Gen, which, if you've done XState with TypeScript, it's. It's very hard to, you know, just to express everything that XDay could do in TypeScript. But XState code Gen does make that a lot easier.

[1:00:00] It automatically generates the types, for, for XState, and so this does make it a lot easier to work with TypeScript in XState. There's, yeah, there's a lot that I'm working on version five, the creator, that, and other tools. Yeah, just a lot. You know, I think Christian might have touched on this, but I do remain excited about it. It's just the ability to pull out the state machine logic and show it to a non-technical user, whether that's a QA or a business analyst.

[1:00:00] Or even like a just. A business partner who's a subject matter expert and say, this is what I thought you said. Let's click through these and make sure that it responds the way that you want. And they can see this, and in a in a form that's intuitive enough for them to contribute back to you versus you know, you know. The other ways to do this are you show them the app and all kinds of stuff's in the way, and I don't know.

[1:00:00] I feel like that's kind of the unsung hero of all this is the separation of business logic and the ability to visualize it well with what David's currently working on. It sounds like even the non-technical people are going to be able to at least start scaffolding out the actual business rules. Using the visual generator, like the machine non business writing code, and also the other way around, this is something where I'll just Ed it because, you might know that Reactathon is happening in a few days, and I am giving a presentation on, autogeneration of documentation.

[1:01:00] So the idea is that your state machine is a directed graph, you know, mathematically speaking, and given that it's a directed path you or directed graph, you could use things like shortest path algorithms. To basically say, if I want to get to the active state, or if I want to get to a specific state, find me all the paths that go from the initial state to that state and just generate documentation for them, or even generate the different states of the components.

[1:02:00] As we go through each of those states. And then you have a very visual way of representing, like, hey, you want to go through an entire flow. Here's how to do it, and that's something that will stay up. Tod Dat you know, as you know well, whenever you change your machine, it's just automatically generated. So very cool. And then if people do to start, is it the documentation? GitHub where? Where's your like recommended path to get up and running?

[1:02:00] So, there's a few. There's, there's of course the documentation on XState I have here, there is, I also over here. I have a ton of resources and these are just different demos. And articles that people have wrote about XState. And I think there's like over a hundred, maybe like 200 over here, and they range from videos to, you know, other things as well. There's also statecharts. GitHub..io, and this is written by Eric Mogenson.

[1:03:00] It's not, XState specific, instead, it's just a general introduction to statecharts.

[1:03:00] The different parts of, what statecharts are, when you should and shouldn't use statecharts and all of that. And it's just a really good information resource, and there's also a community at spectrum. Chat statecharts, where? for? For statecharts in general, it's a really great place. A lot of people ask XState stuff over here, but there is also, discussions on the XState repo itself. And you could get an idea of the kinds of questions that people are asking about, how do I use XState for this?

[1:03:00] How do I do this with XState? And yeah, there's just a lot of really good discussion over here as well. So there's a few places. There's rumor of ports of XState into other languages like Python and Swift and so on. Can you kind of corroborate any of that? Yeah, I'm actually. I am personally working on XState Python. It's not, released yet, but it's basically the same idea over here. I, there is someone else working on Swift, one of my, or a couple of my co-workers working on C.

[1:04:00] And so they're not necessarily XState ports you could think of. XState is an implementation of the SCXML algorithm, so is XState for Python, and so is a bunch of other libraries too. So, yeah, the whole idea is basically, can we get XState or XState machines working in different languages and sort of testing that theory? So, yeah, that's definitely happening too. Excellent. Must feel nice to see your work spread beyond the original vision.

[1:04:00] Yeah, yeah, and well, I, I wouldn't say it's my work. I'm just, you know, spreading the word of, like, hey, statecharts exist, they've existed for longer than I've been alive. I'm just promoting it, I, at least in, you know, JavaScript in the web. And I'm really glad to see other people who have either worked with statecharts before or learned about it and are. Motivated to make it for other languages? Well, we look to your for old technology and can't wait to see Punch cards 2.5 get released.

[1:05:00] DAVID Oh yeah, well, David, this has been like, really, really awesome. I've definitely learned a lot. If if people want to follow you and like, reach out at all is, is Twitter the best place? How can they follow everything you do? Yeah, I would say Twitter is a good place to do it. I'm on there more often than I should be. So, yeah, for sure, it's at David K. Piano, okay, and I'll toss that in chat as well.

[1:05:00] Let's do that. And one thing we like to wrap up with is just any plugs that we have about various things.

[1:06:00] And it can be Tech related or otherwise. Dan, you always like to go first for this. Yeah, I'll throw out the newsletter again, the Enterprise React newsletter. What's cool is our developers are the ones who submit the article, so it's by developers for developers, and we never spam. I will throw that in chat. Kristen, do you have anything else that You' like to plug? No, nothing coming up, David, anything. Anything you want to recommend here can be Tech related or otherwise, or if it's just EAte that works too.

[1:06:00] Yeah, sure, be. Besides state machines, I also really love doing animations, and I do it with my buddy, U.h. Stephen Shaw, who works over at Codepen. And we have this stream called the key Framers, it's not on Twitch, it's on YouTube, and so if you go to key frame.. R.S. That's just a whole bunch of information. And a lot of the things we do are actually just like applying these state machine principles to doing these really complex animations.

[1:07:00] And I'm talking like, we, we'll pull animations from dribble, like the ones that look really cool. And be like, let's see if we could recreate this in an hour or two. So we've seen some of your CSS animations, and TJ and I both had to pick our Jaws up off the floor. CSS has always befuddled me, and I can't imagine ever making an an animated wolf out of it. Yeah, one day we're gonna have to have you on to just do an extended.

[1:07:00] Session on just how you do those? Because I even feel like I. I'm usually pretty proud of my CSS knowledge, but when I see things like that, it's very humbling. Like it's using like, a very niche way of using CSS. That, like, my brain, has a hard time processing and working around. Yeah, that'd be fun. It's even on some of those like, I have to change the code just to verify. What I'm seeing is actually real.

[1:07:00] Sort of thing. Like, if I remove the ear, does it actually remove the ear? Then it does like, dang it, it is real. Oh, just one last thing, David, you did say you're speaking soon, right?

[1:08:00] Where? What conference was that? So that's at Reactathon, I'll drop that in there. Get a link to that too here. Well, even more. David K. Piano Reacton as the way place to do it, and I'll just plug the. So. We actually did a redesign of the React Wednesday's website, so I'll throw that in chat as well. So if you haven't seen that before, it's a pretty cool design, it's new. We've got videos of all the old shows, so if you want to look through, see previous streams that we've done, and also we do these every Wednesday one o'clock Eastern, same clock.

[1:08:00] We did this today. I, I don't have this on the website yet, but we have Joe Carlson from MonGoDB coming on next week to talk some database stuff, which should be pretty fun. So H, check it out. We're here every Wednesday. So other than that, thanks so much David again, this was. This was really cool, really. Appre. Appreciate you taking the time to show us, teach us about state machines and next state.

[1:08:00] Yeah, thank you all for having me. It's been great. All right guys, until next week. See you everybody, Adios.
