Implement the State pattern / a finite state machine. How does it replace scattered boolean flags and guard the transitions a UI can make?
Recognising 'boolean soup' (isLoading/isError/isSuccess) and modeling it as explicit states with legal transitions.
The State pattern lets an object change its behavior when its internal state changes — it looks like the object changed class. Concretely, you model the system as a finite state machine (FSM): a set of named STATES, and a table of legal TRANSITIONS mapping (currentState, event) to the next state. The signal is 'boolean soup' — a component juggling `isLoading`, `isError`, `isSuccess`, `isEmpty` where impossible combinations (loading AND error) are representable and creep in as bugs, and behavior is decided by tangled `if` chains scattered across handlers. Modeling it as ONE state variable that can only be `idle | loading | success | error` makes illegal states UNREPRESENTABLE, centralises 'what can happen next' in the transition table (an event that isn't legal for the current state is simply ignored or throws), and makes the logic self-documenting and testable. Each state can also carry state-specific behavior/data. This is exactly what a traffic light, a checkout flow, a media player (playing/paused/stopped), a form wizard, and async data-fetching are — and it's why XState and the useReducer 'state machine' pattern are popular in React: a reducer keyed on the current state plus an action IS an FSM. Contrast with Strategy (js-41): both delegate behavior, but Strategy is picked by the client for a single call and the strategies are independent, whereas State transitions are driven by the machine itself as events arrive, and states are aware of which states follow. The payoff is fewer impossible-state bugs and a clear map of allowed flows; the cost is upfront modeling, so use it when a thing has genuinely distinct modes with rules about moving between them.
Anything with distinct modes and rules for moving between them — async fetch status, wizards/checkout, media players, connection lifecycles; pairs with useReducer / XState.
O(1) per transition (table lookup).