Light Bulb
The smallest machine worth writing: two states, Off and On, and a single toggle event that flips between them. It is the “hello world” of state machines — just enough to see the engine, its lifecycle hooks, and nothing else.
Try it
Click Toggle to dispatch the toggle event. The statechart highlights the active state; the log records each transition.
The configuration
const config = {
key: "LightBulb",
transitions: [
["", "*", "Off"], // initial: enter Off
["Off", "toggle", "On"], // Off + toggle → On
["On", "toggle", "Off"], // On + toggle → Off
],
};
The first triple is the initial transition: "" as the source means “on start, go here,” and "*" matches any event. The other two are the toggle cycle.
Wiring behaviour with the engine
Register one onStateCreate callback. It fires for every state the machine creates; attach that state’s onEnter / onExit hooks inside it.
import { FsmProcess } from "@statewalker/fsm";
const process = new FsmProcess(config);
process.onStateCreate((state) => {
state.onEnter(() => console.log("→", state.key));
});
await process.dispatch(""); // enter Off
await process.dispatch("toggle"); // Off → On
await process.dispatch("toggle"); // On → Off
That is the whole example. dispatch("") enters the initial state; each dispatch("toggle") flips it.
The same thing with startProcess
If you would rather not manage onStateCreate yourself, the runner does the wiring. You return the handlers for each state from a single load callback:
import { startProcess, KEY_DISPATCH } from "@statewalker/fsm";
const context = {};
await startProcess(context, config, (stateKey) => {
if (stateKey === "On") return [() => console.log("💡 on")];
if (stateKey === "Off") return [() => console.log("· off")];
return [];
});
await context[KEY_DISPATCH]("toggle"); // 💡 on
Next
- Traffic Light — a machine that advances itself with timed events.
- Getting Started — the engine, step by step.