• 第58节——redux-toolkit中的createAsyncThunk


    一、概念

    createAsyncThunk 是一个由 Redux Toolkit 提供的函数,用于创建处理异步操作的 thunk action creator。使用 createAsyncThunk 可以简化 Redux 中处理异步操作的流程,使代码更加清晰、简洁。

    二、参数说明

    import { createAsyncThunk } from "@reduxjs/toolkit";
    
    const myAsyncThunk = createAsyncThunk(
      /**
       * 一个字符串类型的 action 名称,用于在 Redux 中识别该 action。
       * 该名称通常包含操作名称和状态
       *  */
      "myAsyncOperationStatus",
      /**
       * 异步操作函数,该函数接收两个参数
       * 第一个参数是 thunk 的 payload,也就是调用的时候传过来的
       * 第二个参数是thunk对象
       * dispatch
       * 用于 dispatch 其他 action 的函数
       * getState
       * 用于获取当前 Redux store 中的 state 的函数
       * extra
       * 性是用于传递额外参数的对象
       * 
       */
      async (arg, { dispatch, getState, extra }) => {
        // 异步操作函数,必须返回一个 Promise
        const response = await fetch("https://example.com/api/someEndpoint");
        return response.json();
      },
      {} // 可选的配置项
    );
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27

    三、例子

    点击按钮age延迟1秒后+1,在延迟的时候,显示loading。偶数的时候显示报错,并显示提示信息

    1、在action目录的user.js文件添加一下代码

    import { createAction, createAsyncThunk } from "@reduxjs/toolkit";
    
    const dely = () => {
      return new Promise((resolve, reject) => {
        setTimeout(() => {
          resolve();
        }, 1000);
      });
    };
    
    export const ageAddAsync = createAsyncThunk(
      "user/ageAddAsync",
      async (arg, { dispatch, getState, extra }) => {
        const { user } = getState();
        console.log(user.age);
        await dely();
        // 偶数的时候抛错
        if (user.age % 2 === 0) {
          throw new Error("偶数的时候抛错")
        }
      }
    );
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22

    2、修改slice目录里的user.js模块

    import { createSlice } from "@reduxjs/toolkit";
    import { ageAddAsync } from "./../actions/user";
    
    const userSlice = createSlice({
      // 切片名 必须全局唯一
      name: "user",
      // 初始化状态
      initialState: {
        age: 1,
        name: "李四",
        status: "",
        error: "",
      },
    
      reducers: {
        /**
         *
         * @param {*} state 当前的state
         * @param {*} action 穿过来的参数
         */
        addAge(state, action) {
          return {
            ...state,
            age: state.age + 1,
          };
        },
      },
      extraReducers: (builder) => {
        builder
          .addCase("user/updateName", (state, action) => {
            state.name = action.payload.name;
          })
          // 异步方法的pedding状态
          .addCase(ageAddAsync.pending, (state) => {
            state.status = "loading";
          })
          // 异步方法的成功的状态
          .addCase(ageAddAsync.fulfilled, (state, action) => {
            state.age += 1;
            state.status = "successed";
            state.error = ''
          })
          /**
           * state
           * action 当前的错误信息
           */
          .addCase(ageAddAsync.rejected, (state, action) => {
            console.log(action)
            state.status = "error";
            state.age += 1
            state.error = action.error.message;
          });
      },
    });
    
    /**
     * 导出slice模块的reducer
     */
    export default userSlice.reducer;
    
    /**
     * 直接导出actions模块
     * 这个actions里面的方法和reducer里的方法名
     * 一致,直接对象解构
     */
    export const { addAge } = userSlice.actions;
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66

    3、挂载到configureStore

    import { configureStore, createSlice } from "@reduxjs/toolkit";
    import user from './slice/user';
    
    const store = configureStore({
      reducer: {
        user
      },
    });
    
    export default store;
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    4、页面中使用

    import { useSelector, useDispatch } from "react-redux";
    import { ageAddAsync } from "./store/actions/user";
    
    export default function LearnReduxToolkit4() {
      const user = useSelector((state) => state.user);
      const dispatch = useDispatch();
    
      return (
        
    {user.name}--{user.age}
    {user.status}
    {user.error}
    {/*
    偶数抛出错误
    */}
    ); }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19

    四、小思考

    可以不可以封装一下createSlice和createAsyncThunk,让调用变得更简单🤔

  • 相关阅读:
    产品思维训练 | 小程序分类管理将有什么影响?
    WIFI功耗计算器
    VR结合|山海鲸虚拟展厅解决方案
    【Elasticsearch】kibana 操作es文档详细总结
    esp32s3通过mqtt协议连接阿里云(wifi+mqtt+vscode+espidf4.4.4+py3.8.7)
    用面向对象的方式操作 JSON 甚至还能做四则运算 JSON 库
    2022国赛C题解析
    谣言检测()《Data Fusion Oriented Graph Convolution Network Model for Rumor Detection》
    【漏洞复现】Django _2.0.8_任意URL跳转漏洞(CVE-2018-14574)
    电阻的分类介绍
  • 原文地址:https://blog.csdn.net/weixin_57017198/article/details/133796912