一、React-Redux 核心流程与概念
核心角色
- Store:全局状态容器,管理所有数据。
- Slice:模块化状态管理单元(如学生模块)。
- Actions:描述状态变化的指令(同步或异步)。
- Reducers:根据 Action 处理状态变化的函数。
- Provider:将 Store 注入 React 应用。
- Hooks:组件中访问状态或派发 Action。
二、Redux 配置与核心 API
1. configureStore
-
作用:创建 Redux Store。
-
常用参数:
reducer:根 reducer(可组合多个 Slice)。middleware:自定义中间件(默认已包含redux-thunk)。devTools:是否启用 Redux DevTools(默认true)。
-
示例:
// store.js import { configureStore } from '@reduxjs/toolkit'; import studentReducer from './StuSlice'; export default configureStore({ reducer: { student: studentReducer, }, });
2. createSlice
-
作用:创建包含
reducer和actions的模块化状态单元。 -
参数:
name:Slice 名称(用于生成 Action 类型前缀)。initialState:初始状态。reducers:定义同步 Action 及其处理函数。extraReducers:处理异步 Action(如createAsyncThunk触发的 Action)。
-
示例:
// StuSlice.js import { createSlice, createAsyncThunk } from '@reduxjs/toolkit'; export const fetchStudents = createAsyncThunk( 'student/fetchStudents', async () => { const response = await fetch('/api/students'); return response.json(); } ); const studentSlice = createSlice({ name: 'student', initialState: { data: [], status: 'idle' }, reducers: { addStudent: (state, action) => { state.data.push(action.payload); }, deleteStudent: (state, action) => { state.data = state.data.filter(stu => stu.id !== action.payload); }, }, extraReducers: (builder) => { builder .addCase(fetchStudents.pending, (state) => { state.status = 'loading'; }) .addCase(fetchStudents.fulfilled, (state, action) => { state.status = 'succeeded'; state.data = action.payload; }); }, }); export const { addStudent, deleteStudent } = studentSlice.actions; export default studentSlice.reducer;
3. createAsyncThunk
-
作用:创建异步 Action,处理与后端的交互(如 CRUD 操作)。
-
参数:
type:Action 类型前缀(如'student/fetchStudents')。payloadCreator:异步函数,返回 Promise。
-
返回值:触发三个 Action 生命周期:
pending:开始请求。fulfilled:请求成功。rejected:请求失败。
-
示例:
export const updateStudent = createAsyncThunk( 'student/updateStudent', async ({ id, newData }) => { const response = await fetch(`/api/students/${id}`, { method: 'PUT', body: JSON.stringify(newData), }); return response.json(); } );
三、React-Redux 组件与 Hooks
1. Provider
-
作用:将 Store 注入 React 应用,使子组件可访问状态。
-
使用场景:包裹根组件。
-
示例:
// index.js import React from 'react'; import ReactDOM from 'react-dom'; import { Provider } from 'react-redux'; import store from './redux/store'; import App from './App'; ReactDOM.render( <Provider store={store}> <App /> </Provider>, document.getElementById('root') );
2. useSelector
-
作用:从 Store 中提取状态数据。
-
使用场景:组件中读取全局状态。
-
示例:
import { useSelector } from 'react-redux'; function StudentList() { const students = useSelector((state) => state.student.data); const status = useSelector((state) => state.student.status); if (status === 'loading') return <div>Loading...</div>; return ( <ul> {students.map((stu) => ( <li key={stu.id}>{stu.name}</li> ))} </ul> ); }
3. useDispatch
-
作用:获取
dispatch函数,用于派发 Action。 -
使用场景:组件中触发状态更新(同步或异步)。
-
示例:
import { useDispatch } from 'react-redux'; import { addStudent, deleteStudent } from './redux/StuSlice'; function AddStudentForm() { const dispatch = useDispatch(); const handleSubmit = (e) => { e.preventDefault(); const newStudent = { id: Date.now(), name: e.target.name.value }; dispatch(addStudent(newStudent)); }; return ( <form onSubmit={handleSubmit}> <input name="name" /> <button type="submit">Add</button> </form> ); }
四、异步操作处理流程
典型异步操作步骤
- 定义异步 Thunk:使用
createAsyncThunk创建异步 Action。 - 处理生命周期:在 Slice 的
extraReducers中处理pending/fulfilled/rejected。 - 派发 Action:在组件中通过
dispatch(fetchStudents())触发异步操作。 - 更新 UI:通过
useSelector监听状态变化(如status或data)。
五、总结表格
| API/组件 | 作用 | 核心参数/方法 |
|---|---|---|
configureStore | 创建 Redux Store | reducer, middleware |
createSlice | 创建模块化状态单元 | name, initialState, reducers, extraReducers |
createAsyncThunk | 创建异步 Action | type, payloadCreator |
Provider | 注入 Store 到 React 应用 | store |
useSelector | 获取 Store 中的状态 | selector 函数 |
useDispatch | 获取 dispatch 函数 | 无 |
六、常见场景示例
异步数据加载与错误处理
// StuSlice.js 中补充 extraReducers
extraReducers: (builder) => {
builder
.addCase(fetchStudents.pending, (state) => {
state.status = 'loading';
})
.addCase(fetchStudents.fulfilled, (state, action) => {
state.status = 'succeeded';
state.data = action.payload;
})
.addCase(fetchStudents.rejected, (state, action) => {
state.status = 'failed';
state.error = action.error.message;
});
};
组件中触发异步操作
import { useDispatch } from 'react-redux';
import { fetchStudents } from './redux/StuSlice';
function StudentPage() {
const dispatch = useDispatch();
// 初始化时加载数据
useEffect(() => {
dispatch(fetchStudents());
}, [dispatch]);
// ...其他逻辑
}