Redux in React.js with Redux Toolkit

Musab Abbasi
6 min readNov 6, 2022

For the beginner it is often seems difficult to learn Redux. There might be few reasons, it can be that people have made it look difficult to learn or you might have not found a good tutorial.

In this article, I will be discussing and practically showing the implementation of Redux in React.js with Redux Toolkit.

Pre-requisite:

  1. You must have basic concepts of React and have working knowlegde of it.

What is Redux?

Redux is a predictable state container designed to help you write JavaScript apps that behave consistently across client, server, and native environments, and are easy to test.

While it’s mostly used as a state management tool with React, you can use it with any other JavaScript framework or library. (source)

When and why to use Redux?

Redux allows you to manage your app’s state in a single place and keep changes in your app more predictable and traceable. It makes it easier to reason about changes occurring in your app. But all of these benefits come with tradeoffs and constraints. One might feel it adds up boilerplate code, making simple things a little overwhelming; but that depends upon the architecture decisions.

One simple answer to this question is you will realize for yourself when you need Redux. If you’re still confused as to whether you need it, you don’t. This usually happens when your app grows to the scale where managing app state becomes a hassle; and you start looking out for making it easy and simple. (source)

Now since you are clear about what is redux and when to use it. Let’s talk about Redux Toolkit.

Redux Toolkit

Redux Toolkit is a set of tools that helps simplify Redux development. It includes utilities for creating and managing Redux stores, as well as for writing Redux actions and reducers. The Redux team recommends using Redux Toolkit anytime you need to use Redux.

Let’s get started!

To get started we will first create our React.js folder using “npx create-react-app redux”

npx create-react-app redux

Once it completes you will see this:

Next, we will install dependencies. To install app the required dependences we will execute the below command.

npm install react-redux redux @reduxjs/toolkit

Now once the above command is successfully executed, we will add a folder called app in our source folder of frontend.

Next, we will add another folder in our new “app” folder called “features”. We will be adding all of our slices in it.

Hold On! Let’s learn above few more concepts

What is CreateSlice

A function that accepts an initial state, an object of reducer functions, and a “slice name”, and automatically generates action creators and action types that correspond to the reducers and state.

This API is the standard approach for writing Redux logic.

Internally, it uses createAction and createReducer, so you may also use Immer to write "mutating" immutable updates. Read More at createSlice | Redux Toolkit (redux-toolkit.js.org)

Reducers

An object containing Redux “case reducer” functions (functions intended to handle a specific action type, equivalent to a single case statement in a switch).

The keys in the object will be used to generate string action type constants, and these will show up in the Redux DevTools Extension when they are dispatched. Also, if any other part of the application happens to dispatch an action with the exact same type string, the corresponding reducer will be run. Therefore, you should give the functions descriptive names. Read More at createSlice | Redux Toolkit (redux-toolkit.js.org)

Now, let’s say we have a logged in user and we wanted to save their details using redux so that we can access it from anywhere in our frontend. To do that I will make another folder “user” in features folder, and inside it I will create a file called userSlice.js.

Then, I will add store.js file in our “app” folder. Our folder structure will now look like this.

Next, we will edit our userSlice file. We will add the below code in it.

const { createSlice } = require("@reduxjs/toolkit");const initialState = {
value: {}
}
export const userSlice = createSlice({
name: 'user',
initialState,
reducers: {
setUser: (state, action) =>{
console.log(action)
state.value = action.payload
}
}
})
export const { setUser } = userSlice.actionsexport default userSlice.reducer;

Now what did we just do?

Firstly, we imported createSlice from redux toolkit so that we can make our user slice. Now the createSlice takes few parameters, like name i.e. ‘user’ here and initial state that we currently have an empty object in it. Then we define reducers. Here if have made a reducer called setUser so that I can set user details in the user value object. Then, we exported setUser function and default userSlice.

Now what exactly this setUser doing? Well, it is setting the new value in our current state. So, we are getting two values i.e. state which is the current state and action. Our action will contain multiple values, but we will be using payload here. Payload is the data sent to it.

Now since we have created our user slice, to make use of it we have to add it in our store.

import { configureStore } from '@reduxjs/toolkit'import userReducer from './features/user/userSlice';export const store = configureStore({reducer: {user: userReducer}})

Now it might look complicated at first but we just imported userSlice as userReducer and configureStore from redux toolkit. Then, we simply exported our store with userReducer in it.

Now let’s put it to test. First to use our store we need to wrap our app.js in redux provider. Now we will replace the complete code in our index.js with following code.

import React from 'react'import ReactDOM from 'react-dom'import './index.css'import App from './App'import { store } from './app/store'import { Provider } from 'react-redux'ReactDOM.render(<Provider store={store}><App /></Provider>,document.getElementById('root'))

Here we just imported Provider, wrap <App /> around it and passes our store.

Now we will test it in our app.js.

First I will remove the whole app.js code with this one.

function App() {return (<div className=""></div>);}export default App;

Now we will import useSelector and useDispatch in our file. UseSelector will let us get current value of user in our store and useDispatch will help us execute setUser function. First we will look at how to get user value.

import { useDispatch, useSelector } from "react-redux";function App() {let user = useSelector(state=>state.user.value)return (<div className="">{user?.name}</div>);}export default App;

Now here I am saving current user details in user and displaying user name if exists. Now initially we do not have any data in our user slice so you will see blank page but to set user data we will do something like this.

import { useEffect } from "react";import { useDispatch, useSelector } from "react-redux";import { setUser } from "./app/features/user/userSlice";function App() {let dispatch = useDispatch();let user = useSelector(state=>state.user.value)function newUser(){dispatch(setUser({ name: 'Musab Abbasi'}))}return (<div className="">{user?.name}<br /><button onClick={()=>newUser()}>Set User</button></div>);}export default App;

Here we are setting a new user value on click of a button. Currently the value is hardcoded, but it can become dynamic. We are using dispatch/useDispatch to trigger setUser and editing the user value.

Now you have an idea on how to use Redux with Redux Toolkit in React.js. You can make more complicated applications using it. I would recommend reading about redux-logger and redux-persist.

GitHub Repo for this article: MuqtadirBillah/redux-toolkit (github.com)

Now you know one of the best project structure for node.js and express.js based server.

Follow me for more interesting tips and tricks at Musab Abbasi — Medium
You can also find me on LinkedIn and Github

--

--

Musab Abbasi

Computer Science Graduate with MERN stack website development expertise.