使用 redux-toolkit 处理错误

Рич*_*ман 8 redux react-redux redux-toolkit

我的案例中有关错误的信息深深地存在于响应中,我正试图将我的项目移至redux-toolkit. 这是以前的样子:

catch(e) {
  let warning
  switch (e.response.data.error.message) { 
    ...
  }
}
Run Code Online (Sandbox Code Playgroud)

问题是redux-toolkit没有将这些数据放在rejected动作创建者中,而且我无法访问错误消息,它将他的消息而不是最初的消息:

在此处输入图片说明

虽然原始响应如下所示:

在此处输入图片说明

那么我怎样才能检索到这些数据呢?

mar*_*son 12

根据文档,RTKcreateAsyncThunk具有默认的错误处理方式——它将Error实例的序列化版本作为action.error.

如果您需要自定义rejected操作中的内容,则由您自己捕获初始错误,并用于rejectWithValue()决定操作中的内容

const updateUser = createAsyncThunk(
  'users/update',
  async (userData, { rejectWithValue }) => {
    const { id, ...fields } = userData
    try {
      const response = await userAPI.updateById(id, fields)
      return response.data.user
    } catch (err) {
      if (!err.response) {
        throw err
      }

      return rejectWithValue(err.response.data)
    }
  }
)
Run Code Online (Sandbox Code Playgroud)

  • 如果您想发出请求而不传递任何数据,则必须执行类似 async ( _ , {rejectWithValue }) => { .... (3认同)
  • 这是非常奇怪的默认行为,而不是按原样返回错误 - 但是,是的,这是文档记录的。令人烦恼的是必须添加样板 `try { return await thing() } catch (error) { returnrejectWithValue(error) }` 而不仅仅是 `return thing()`。 (3认同)
  • 我认为这也很糟糕。就我而言,基本上我的所有调用都需要这个,因为我可以从服务器返回自定义错误并希望显示适当的错误消息,这也可能执行一些代码或自定义行为,并且在意外错误中向服务器显示一些默认错误消息用户。事实上,javascript(与其他语言相反)只允许错误对象具有消息字段本身就已经很糟糕了,但是 redux 工具包的这种行为使事情变得更糟:/现在我创建了一个执行此逻辑的自定义函数,但仍然使通话有点污染。 (3认同)

小智 7

我们使用thunkAPI,payloadCreator 中的第二个参数;包含通常传递给 Redux thunk 函数的所有参数,以及其他选项:对于我们的示例,async(obj, {dispatch, getState, rejectWithValue, fulfillWithValue})我们的 PayloadCreator 具有所需的参数;

这是使用fetch api 的示例

import { createSlice, createAsyncThunk } from "@reduxjs/toolkit";

export const getExampleThunk = createAsyncThunk(
    'auth/getExampleThunk',
    async(obj, {dispatch, getState, rejectWithValue, fulfillWithValue}) => {
        try{
            const response = await fetch('https://reqrefs.in/api/users/yu');
            if (!response.ok) {
                return rejectWithValue(response.status)
            }
            const data = await response.json();
            return fulfillWithValue(data)
        }catch(error){
            throw rejectWithValue(error.message)
        }
    }
)   
Run Code Online (Sandbox Code Playgroud)

切片中的简单示例:

const exampleSlice = createSlice({
    name: 'example',
    initialState: {
        httpErr: false,
    },
    reducers: {
        //set your reducers
    },
    extraReducers: {
        [getExampleThunk.pending]: (state, action) => {
            //some action here
        },
        [getExampleThunk.fulfilled]: (state, action) => {
            state.httpErr = action.payload;
        },
        [getExampleThunk.rejected]: (state, action) => {
            state.httpErr = action.payload;
        }
    }
})
Run Code Online (Sandbox Code Playgroud)

处理错误

请注意: rejectWithValue- 实用程序(来自 thunkAPI 的附加选项),您可以在操作创建者中返回/抛出该实用程序,以返回带有定义的有效负载和元的拒绝响应。它将传递您赋予它的任何值,并将其返回到被拒绝操作的有效负载中。