Redux Toolkit
Redux Toolkit is the official, opinionated, batteries-included toolset for efficient Redux development. It simplifies the most common Redux use cases and reduces boilerplate code.
Overview
Redux Toolkit (RTK) includes utilities to simplify the most common Redux use cases, including store setup, creating reducers, immutable update logic, and more.
What You'll Learn
Core Concepts
- Store configuration with
configureStore() - Slice creation with
createSlice() - Async logic with
createAsyncThunk() - Entity management with
createEntityAdapter()
Key Benefits
- Less boilerplate: Write less code to accomplish the same tasks
- Immutable updates: Built-in Immer integration for easier state updates
- DevTools integration: Automatic Redux DevTools setup
- TypeScript support: First-class TypeScript integration
Installation
# NPM
npm install @reduxjs/toolkit react-redux
# Yarn
yarn add @reduxjs/toolkit react-redux
Basic Example
import { configureStore, createSlice } from '@reduxjs/toolkit'
// Create a slice
const counterSlice = createSlice({
name: 'counter',
initialState: { value: 0 },
reducers: {
increment: (state) => {
state.value += 1
},
decrement: (state) => {
state.value -= 1
}
}
})
// Configure store
const store = configureStore({
reducer: {
counter: counterSlice.reducer
}
})
export const { increment, decrement } = counterSlice.actions
export default store
Key APIs
configureStore()
- Wraps
createStore()with good defaults - Automatically sets up Redux DevTools
- Includes redux-thunk by default
- Adds development-only middleware
createSlice()
- Generates action creators and action types
- Uses Immer for immutable updates
- Reduces boilerplate significantly
createAsyncThunk()
- Handles async logic and lifecycle actions
- Automatically dispatches pending/fulfilled/rejected actions
- Integrates with extraReducers
createEntityAdapter()
- Provides standardized way to store collections
- Includes CRUD utilities
- Optimizes for normalized state shape
Project Structure
src/
store/
index.js # Store configuration
slices/
authSlice.js # Auth-related state
todosSlice.js # Todos state
userSlice.js # User profile state
components/
hooks/
useAppDispatch.js # Typed dispatch hook
useAppSelector.js # Typed selector hook
Best Practices
- Use createSlice for most reducers
- Use createAsyncThunk for async logic
- Structure slices by feature, not by type
- Use TypeScript for better developer experience
- Keep state normalized when dealing with collections
Common Patterns
Async Data Fetching
const fetchUsers = createAsyncThunk(
'users/fetchUsers',
async () => {
const response = await api.fetchUsers()
return response.data
}
)
Entity Management
const usersAdapter = createEntityAdapter()
const usersSlice = createSlice({
name: 'users',
initialState: usersAdapter.getInitialState(),
reducers: {
userAdded: usersAdapter.addOne,
userUpdated: usersAdapter.updateOne
}
})
Next Steps
- Set up your first store - Configure store with createStore
- Create your first slice - Build a simple counter or todo slice
- Add async logic - Implement data fetching with createAsyncThunk
- Learn advanced patterns - Entity adapters, RTK Query, and more