State as a function of actions
A reducer is a pure function that takes the current state and an action, and returns the next state. All state changes flow through this one function, which makes transitions predictable and testable.
- The action describes what happened, usually a type and a payload.
- The reducer switches on the action type to compute the new state.
- It must be pure: no mutation, no side effects, same output for same input.
Why teams reach for it
When many actions can change overlapping state, scattered setters become hard to follow. Centralizing transitions has clear payoffs.
- Every change is named, so logs read like a history.
- Time travel debugging and undo become possible from the action list.
- The reducer is trivial to unit test in isolation.
Side effects like network calls live outside the reducer, in middleware or effect handlers, so the reducer stays pure. Keep actions describing events that happened, not commands, so the same action can drive multiple reducers.
Key idea
Route all changes through a pure reducer of state and action, keeping side effects outside so transitions stay predictable and testable.