As applications grow so does complexity and the handling of state. Redux is a state container (a client-side database) that solves this problem. In a series of three we will look into Redux and take a peek at the fundamentals.
This blog post is suitable for intermediate front end developers who are starting out with Redux. A common pain point when building large-scale applications is the tight coupling between user interactions and state changes.
For example, consider an app for managing email. Clicking an email must:
Replace the “inbox view” (the list of emails) with the “email view” (the email the user clicked)
Mark the email as read locally
Reduce the total unread counter locally
Change the URL of the browser
Send a web request to mark the email as read on the server
There is a lot of state handling going on here. The function in the top-level component that handles a user clicking on an email must describe all the state changes that occur.
Redux has only about 100 lines of code (stripped and minified), so it is actually possible to look into the code itself and understand it without too much of an effort.
While flux have dispatchers and allow multiple stores, Redux simply dispatches actions and passes the current state through one immutable store and returns the new state.
If the new state differs from the current state it will trigger an action that will re-render the ui that care in your application.
Are you confused yet? Well, I was at first. Soon we will hopefully get som clarity. Let’s take a look at the three core principles of Redux.
3 core principles of Redux
Redux has three core principles that you need to understand:
One Immutable store
Actions trigger changes
Reducers update state
The first principle is that all application state is kept in one immutable store. Having one immutable store makes debugging and testing easier, allows server rendering and actions like redo / undo possible.
The second principle is that when a user performs an action i.e. clicks on a submit button in a form (a user intent). It triggers a change and passed on to the store.
A reducer (a simple “pure” function that takes two parameters: the current state and an action) picks up the action which then returns the new state. This is the third principle.
React – Hey CourseAction, someone clicked this “Save Course” button. Action – Thanks React! I will dispatch an action so reducers that care can update state.
Reducer – Ah, thanks action. I see you passed me the current state and the action to perform. I’ll make a new copy of the state and return it. Store – Thanks for updating the state reducer. I’ll make sure that all connected components are aware. React-Redux – Woah, thanks for the new data Mr. Store. I’ll now intelligently determine if I should tell React about this change so that it only has to bother with updating the UI when necessary.
Hopefully this gives you an idea of the flow in Redux. In next episode we will look into more detail how this looks in code.
When to use Redux?
So when to use React only and when to add Redux on top of that? The answer to when you should add in Redux is a matter of preference. Pete Hunt described it like this:
If you aren’t sure if you need it, you don’t need it – Pete Hunt on Flux and Redux
If you find that the handling of state at the top-level component is getting out of hand and is hard to manage – that is an indicator that you should consider adding Redux to your application.
So when is that? From my experience, when building a typical CRUD app, Its fair to say its time to bring in Redux and declare actions like Create, update, delete to be passed through the store.
In this episode of “An introduction to Redux for beginners” we have looked at the fundamentals of Redux and when and why it can be used. In the next episode, we will look at some hands-on code examples and how to structure Redux on a fundamental level.