Who needs state management anyways?

Yaron Biton
4 min readFeb 27, 2017

--

If you are in the frontend scene, you are probably aware of the recent debate about state management and when it is actually needed. My opinion is that it is super relevant almost everywhere. Let me elaborate.

Background

Building Frontends - Single page applications, is complex because
there is so much state.

Some of this state is arriving at the front via AJAX or websockets but much of this state has nothing to do with the server, examples: isPlaying, isTyping, selectedItems, currWizardStep.

the real issue is data changing over time and efficient re-rendering (when the page is big, DOM access is expensive) modern applications has a lot of that - shared mutable state is a pain!

In the past (i.e. Angular 1) it was not uncommon to have bits and pieces of state strewn across our application tucked inside of controllers, services, routes, directives, and templates.

It is known that when the application grows, this approach is hard to scale, and modern Angular apps look something like this.

Enters Flux - Redux

Just as modern web frameworks like Angular 1 permanently altered our jQuery-centric approach to app development, React has fundamentally changed the way that we approach state-management. Redux is front and center of this shift as it introduced an elegant, yet profoundly simple way to manage application state.

When embracing Flux, the only way to change state is by firing an action to the store, the store will modify the state and then emit an event that will cause the component to fetch the new state.

Here is the basic implementation for the redux store:

And here is a basic usage of the flow:

Basic Redux flow

This idea was also adopted by modern frameworks such as Angular (2) and VueJS and the idea of one-way-data-flow was even ported back to Angular 1.

The Angular Way

Angular is a sophisticated framework from the house of google that relies on two corner stones from the house of Microsoft: Typescript and RxJS, it is useful for building enterprise level applications, with many forms and many developers.

As RxJS Observables are already used inside Angular, the reactive nature of state updates is commonly achieved by using something like ngrx/store. those will encourage us to code pure reducers to mutate the state.

Making our state type-safe also comes with a price of its on, so we need a solution for describing those types without repeating ourselves, something like this: https://gist.github.com/vyaron/c8d71d268aa9d7e30ff3d1c15d236b84

As objects fly around the system by reference, and due to the shallow and weak implementation of JS consts, it is necessary to prevent direct mutations, so we need to plug in an immutability solution either by creating clones manually or by using something like immutable.js.

Combined with the smart-dumb components paradigm and the OnPush change detection strategy, this will eventually lead us to a full solution for detecting changes and efficiently re-rendering the components.

But this does not end here as we also need a pattern for achieving un-pure operations like server communications, so plugging in another aspect or a library like ngrx/effects to manage these operations.

Works? Yes. Crazily complicated? Yes.

The VueJS Way

VueJS is the new kid in the block of JS framework, and many developers’ favorite now days.

Vue uses a whole different strategy for change-detection, instead of Angular (1 and 2) dirty checks tactic, that keeps an old value and compare it to current value on any async operation (timeouts, events, ajax, etc — this is done by zone.js), Vue is wrapping our data with a simple getter/setter mechanism (IE9+) so Vue knows about every change before it even happened, it can cache values and monitor their dependencies to trigger re-calculating and re-rendering.

Vue is amazingly simple, so gets you quick wins when building small-medium apps.

But with Vuex - the state management solution for Vue, we can now code enterprise level applications without the hassle, I encourage you to try it out!

The other way?

Some people argue that this Redux hype is out of place and suggest going with the Observable Data Services, so, no reducers just promise / observable based functions that are called directly, so can be easily followed and not indirectly through actions.

Here are some points to consider:

Redux / Vuex has a great systematic debug flow:

  • Actions and states are logged to the console
  • Find the bad state
  • Check the action
    If you see something funny, blame the component
  • Otherwise, fix the reducer
  • Feeling proffesional? Write a test

Going Redux/Vuex make this list of features easily achieved:

  • Persistence and Offline
    State can be stored in local-storage
    Actions can be queued
  • Universal rendering
    Starting the app right into a specific state
  • Recording user sessions, reporting errors
    Try-catch -> send state and action to server!
  • Optimistic mutations
    Update the UI immediately, If we get an error from server, undo.
  • Collaborative editing is simple!
    just send those serializable actions to your peer

Summary

State management is something to plan ahead, it is not something you want to add in late into the project, planning ownership of the application’s state is crucial to your success in building apps that do not gets rotten so quickly.

To get a better picture, and see some code, check out this repo: https://github.com/coding-academy/vuejs-vuex-shopping-cart

--

--