如何在axios catch()块中重新引发捕获的错误

时间:2019-01-22 06:56:43

标签: javascript reactjs axios redux-saga

// ... createStore( helloWorldReducer, railsProps, window.__REDUX_DEVTOOLS_EXTENSION__ && window.__REDUX_DEVTOOLS_EXTENSION__() ) // ... 中,为什么在axios内不允许throw new Error()? 我的要求是,如果服务器返回错误,则catch块应引发错误,稍后将由redux-saga处理并分派适当的操作。

API调用:

catch()

由于上述catch块,我得到export const userSignupApi = userDetails => { const endpoint = `${URL_ROOT}${URN_SIGNUP}`; axios .post(endpoint, userDetails) .then(response => { console.log("Response: ", response); //do something with the response }) .catch(error => { throw new Error(error.response.data.message); }); }; 。 以下是我处理该操作的传奇:

Unhandled Rejection (Error)

编辑:为什么我要上面的代码结构?因为这样可以轻松地对API代码和Saga代码进行单元测试。

3 个答案:

答案 0 :(得分:0)

userSignupAPI中创建的Promise并未在任何地方使用(甚至没有返回),因此当在catch中抛出错误时,Promise链解析为一个(未捕获的)拒绝的Promise ,从而导致错误。

userSignupAPI的呼叫者中,您应该进行await的呼叫,以便try内部的catch / handleUserSignup会看到抛出的错误:< / p>

export const userSignupAPI = userDetails => {
   const endpoint = `${URL_ROOT}${URN_SIGNUP}`;
    return axios
    .post(endpoint, userDetails)
    .then(response => {
      console.log("Response: ", response);
    })
    .catch(error => {
      throw new Error(error.response.data.message);
    });
};

async function* handleUserSignup(action) {
  try {
    yield await call(userSignupApi, action.userDetails);
    yield put(userSignupSuccess()); //dispatching success action
  } catch (error) {
    yield put(userSignupFail(error)); //dispatching error action
  }
}

function* watchUserSignup() {
  yield takeLatest(NEW_USER.SIGNUP, handleUserSignup);
}

(确保call返回Promise返回的userSignupApi

答案 1 :(得分:0)

我已经开始工作了。我做错了。正如@certianPerformance所建议的那样,在阅读了一些问题和github问题之后,我找到了解决此问题的正确方法。我应该返回promise。而不是返回api响应。
这是解决方案:

export const userSignupApi = userDetails => {
  const endpoint = `${URL_ROOT}${URN_SIGNUP}`;

  return axios.post(endpoint, userDetails);
};

传奇:

import { call, takeLatest, put } from "redux-saga/effects";

function* handleUserSignup(action) {
  try {
    const response = yield call(userSignupApi, action.userDetails);
    response.then(response => {
      const location = response.headers.location;
      put(userSignupSuccess(location));
      put(newUserWelcomeNote("Welcome user"));
    });
  } catch (error) {
    const errorMessage = error.response.data.message;
    yield put(userSignupFail(errorMessage));
  }
}

function* watchUserSignup() {
  yield takeLatest(NEW_USER.SIGNUP, handleUserSignup);
}

答案 2 :(得分:-1)

您使用try catch是因为您不想在要在catch中处理的浏览器控制台中引发错误。在catch中抛出错误将删除其目的。如果要抛出错误,请删除try catch(不建议这样做)

更新

对于axios catch方法,捕获由api url引发的任何错误。如果您不想捕获错误并在浏览器中显示它,则可以删除catch块或调用处理错误的操作。有关承诺捕获的更多信息,您可以参考here