bug收集:专门解决与收集bug的网站
网址:www.bugshouji.com
redux新版本移动了@reduxjs/toolkit 这个库中, 不再使用类似redux-thunk等中间件,大大地简化了开发的流程。
今天分享一个@reduxjs/toolkit 实现的一个登录案例,供大家参考
目录结构
|- store
|- index.js 创建store
|- features
|- userSlice.js 用户切片
|- index.js 入口文件
|- pages 页面级组件
|- login.js 登录组件
案例:登录,调用redux中定义的异步数据,并保存数据
features / userSlice.js 的实现
import {createSlice,createAsyncThunk} from '@reduxjs/toolkit'
import service from './../../service'
const initialState={
token:sessionStorage.getItem("token")?sessionStorage.getItem("token"):"",
user:sessionStorage.getItem("user")?JSON.parse(sessionStorage.getItem("user")):{}
}
// 三种状态 ,在extraReducers去侦听,进行不同处理 fulfilled|pending|rejected
export const userLogin = createAsyncThunk("user/userLogin",async (userInput)=>{
// 发起axios请求
const res = await service.userSerive.User_Login(userInput); // 相当于then传的数据
return res;
})
export const {reducer} = createSlice({
name:"userSlice",
initialState,
reducers:{ //纯函数,不能写异步操作
},
extraReducers:{
// userLogin return 的值放在action.payload属性
// payload: 负载
[userLogin.fulfilled](state,{payload}){
state.token = payload.token;
state.user = payload.data;
//将state更新的值同步更新到sessionStorage中
sessionStorage.setItem("token",payload.token);
sessionStorage.setItem("user",JSON.stringify(payload.data));
console.log("fulfilled",payload);
},
[userLogin.pending](state){
console.log("pending");
},
[userLogin.rejected](state){
console.log("rejected");
}
}
})
store/inde.js
import {configureStore} from '@reduxjs/toolkit'
import {reducer} from './features/userSlice'
export const store = configureStore({
reducer:{
userReducer:reducer
}
})
index.js 入口文件
import {Provider} from 'react-redux'
import {store} from './store'
const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
<Provider store={store}>
<App />
</Provider>
);
pages/Login.js
unwrapResult 可用于提取已完成操作的有效负载,实现在组件中拿到action的负载数据.
import { Button, Checkbox,message, Form, Input } from 'antd';
import React from 'react';
import './Login.css'
import {useNavigate} from 'react-router-dom'
import {useDispatch} from 'react-redux'
import {userLogin} from './../store/features/userSlice';
import {unwrapResult} from '@reduxjs/toolkit'
function Login(props) {
const navigate = useNavigate();
const diaptch = useDispatch();
const onFinish = (values) => {
console.log('Success:', values);
// 将用户名和密码发送到后台,进行验证
// 发起请求的操作,redux 中的action中进行
/* Redux工具箱导出一个unwrapResult函数,该函数可用于提取已完成操作的有效负载,
或抛出错误,或抛出rejectWithValue从已拒绝操作创建的有效负载(如果可用)。*/
diaptch(userLogin(values)).then(unwrapResult).then((data)=>{
if(data.returnCode===200){
message.success("登录成功");
navigate("/index");
}else{
message.warning("登录失败");
}
}).catch((err)=>{
message.error("登录出错");
}); // 通过派发到指定action
};
const onFinishFailed = (errorInfo) => {
console.log('Failed:', errorInfo);
};
return (
<div className='loginContainer'>
<h2>登录</h2>
<Form
name="basic"
labelCol={{
span: 8,
}}
wrapperCol={{
span: 16,
}}
initialValues={{
remember: true,
}}
onFinish={onFinish}
onFinishFailed={onFinishFailed}
autoComplete="off"
>
<Form.Item
label="用户名"
name="userName"
rules={[
{
required: true,
message: '请输入用户名!',
},
]}
>
<Input />
</Form.Item>
<Form.Item
label="密码"
name="userPwd"
rules={[
{
required: true,
message: '请输入密码!',
},
]}
>
<Input.Password />
</Form.Item>
<Form.Item
name="remember"
valuePropName="checked"
wrapperCol={{
offset: 8,
span: 16,
}}
>
<Checkbox>记住密码</Checkbox>
</Form.Item>
<Form.Item
wrapperCol={{
offset: 8,
span: 16,
}}
>
<Button type="primary" htmlType="submit">
登录
</Button>
</Form.Item>
</Form>
</div>
);
}
export default Login
苟有恒 , 何必三更眠五更起