Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
189 views
in Technique[技术] by (71.8m points)

javascript - What is the best way to deal with a fetch error in react redux?

I have one reducer for Clients, one other for AppToolbar and some others...

Now lets say that I created a fetch action to delete client, and if it fails I have code in the Clients reducer which should do some stuff, but also I want to display some global error in AppToolbar.

But the Clients and the AppToolbar reducers do not share the same part of the state and I cannot create a new action in the reducer.

So how am I suppose to show global error? Thanks

UPDATE 1:

I forget to mention that I use este devstack

UPDATE 2: I marked Eric's answer as correct, but I have to say that solution which I am using in este is more like combination of Eric and Dan's answer... You just have to find what fits you the best in your code...

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

If you want to have the concept of "global errors", you can create an errors reducer, which can listen for addError, removeError, etc... actions. Then, you can hook into your Redux state tree at state.errors and display them wherever appropriate.

There are a number of ways you could approach this, but the general idea is that global errors/messages would merit their own reducer to live completely separate from <Clients />/<AppToolbar />. Of course if either of these components needs access to errors you could pass errors down to them as a prop wherever needed.

Update: Code Example

Here is one example of what it might look like if you were to pass the "global errors" errors into your top level <App /> and conditionally render it (if there are errors present). Using react-redux's connect to hook up your <App /> component to some data.

// App.js
// Display "global errors" when they are present
function App({errors}) {
  return (
    <div>
      {errors && 
        <UserErrors errors={errors} />
      }
      <AppToolbar />
      <Clients />
    </div>
  )
}

// Hook up App to be a container (react-redux)
export default connect(
  state => ({
    errors: state.errors,
  })
)(App);

And as far as the action creator is concerned, it would dispatch (redux-thunk) success failure according to the response

export function fetchSomeResources() {
  return dispatch => {
    // Async action is starting...
    dispatch({type: FETCH_RESOURCES});

    someHttpClient.get('/resources')

      // Async action succeeded...
      .then(res => {
        dispatch({type: FETCH_RESOURCES_SUCCESS, data: res.body});
      })

      // Async action failed...
      .catch(err => {
        // Dispatch specific "some resources failed" if needed...
        dispatch({type: FETCH_RESOURCES_FAIL});

        // Dispatch the generic "global errors" action
        // This is what makes its way into state.errors
        dispatch({type: ADD_ERROR, error: err});
      });
  };
}

While your reducer could simply manage an array of errors, adding/removing entries appropriately.

function errors(state = [], action) {
  switch (action.type) {

    case ADD_ERROR:
      return state.concat([action.error]);

    case REMOVE_ERROR:
      return state.filter((error, i) => i !== action.index);

    default:
      return state;
  }
}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...