Redux Toolkit
Redux Toolkit is an opinionated approach to utilizing Redux(from the Redux team).
Why?
Instead of wasting time on boilerplate, you can get started immediately. The standards followed are the recommended way to write Redux logic for modern JS applications. I found that I am writing less code for core logic & can see this being utilized in any application that needs state management.
Tools:
https://redux.js.org/ (core library, state management)
https://immerjs.github.io/immer/ (allows you to mutate the state)
https://github.com/reduxjs/redux-thunk (handles async actions)
https://github.com/reduxjs/reselect (simplifies reducer functions)
Set-up:
This example will implement the configureStore()
, useSelector()
, & useDispatch()
tools to run a simple CRUD application. We'll be running off create-react-app for this example.
If you haven’t a react app running yet, run:
npx create-react-app app-name
1.) In the root folder, install react-redux & redux-toolkit:
npm install react-redux @reduxjs/toolkit
2.) Configure the store in a separate store.js
file:
import { configureStore } from “@reduxjs/toolkit”;
export const store = configureStore({
reducer: {},
});
The configureStore()
wraps the createStore
from Redux & provides simple configuration/defaults. We'll add our reducer later.
3.) From here we want to import our store & pass it as a store in our Provider.
import { store } from './store';
import { Provider } from 'react-redux';
const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
<React.StrictMode>
<Provider store={store}>
<App />
</Provider>
</React.StrictMode>
);
4.) Create a features folder in the root & create a Posts.js file:
import { createSlice } from "@reduxjs/toolkit";
const initialState = {
value: [
{id: '1', title: 'title 1', content: 'test'},
{id: '2', title: 'title 2', content: 'test'},
]
}
export const Posts = createSlice({
name: 'posts',
initialState,
reducers: {
addPost: (state, action) => {
state.value.push(action.payload);
},
deletePost: (state, action) => {
state.value = state.value((item) => item.id !== action.payload.id)
}
}
})
export const { addPost, deletePost } = Posts.actions;
export default Posts.reducer;
This is the where the Action logic will go:
state
arg is the draft state provided from Immer.
action
arg is the object being dispatched.
Importing Actions:
export const { addPost, deletePost } = Posts.actions;
Importing Reducers:
export default Posts.reducer;
5.) Import & add the Post reducer to our store:
6.) Create a Posts.js in our component folder & import useSelector
and useDispatch
from the react-redux library:
We can access the state through:
const posts = useSelector(state => state.posts.value);
We can dispatch through:
CreateAsyncThunk:
Summary
With Redux-toolkit we’re able to rid ourselves from having complex store configurations & unnecessary files following boilerplate. I’m planning to add more to this. Highly recommend reading through the Redux-toolkit docs for full comprehension.