Replacing the whole state within a reducer usint R

2019-05-30 20:16发布

the title sounds wired, but what happens if I collect data from a server and in a reducer, I simply want to return these data and set them as the new state.

E.g. fetching data from a backend. Do I really need to make a copy of the previous state if I want to replace it like this:

export function accountData(state = [], action) {
  switch (action.type) {
    case FETCH_FAILURE:
      console.error('SOMETHING BAD JUST HAPPENED');
      break;
    case FETCH_SUCCESS:
        return Object.assign([], state, action.accountData);
    default:
      return state;
  }
}

or would it be ok in this case to just do this:

export function accountData(state = [], action) {
      switch (action.type) {
        case FETCH_FAILURE:
          console.error('SOMETHING BAD JUST HAPPENED');
          break;
        case FETCH_SUCCESS:
            return action.accountData;
        default:
          return state;
      }
    }

1条回答
干净又极端
2楼-- · 2019-05-30 21:00

Yes you can replace the entire state.* Object.assign is simply a convenience method to replace part of the state whilst leaving everything else in tact, and doing so in an immutable fashion. If you're replacing the entire state then it's not necessary to use Object.assign.

(*When I say state I mean the portion of the state for which the reducer is responsible.)

Furthermore it makes no sense to use Object.assign for an array. Object.assign([], state, action.accountData); is semantically equivalent to Object.assign([], action.accountData); That is, it creates a new copy of the array. But since it's an array an not an object, a more explicit and intuitive way to write it would be action.accountData.slice(0) or [...action.accountData]. [CORRECTION: In fact, Object.assign does index-for-index replacement on arrays, which is almost certainly NOT what you want.]

So long as you treat the array is read-only, you can return the array by itself without copying it. So the final way you've written it - return action.accountData; - is perfectly correct.

Finally, I must take issue with the FETCH_FAILURE case. You're not returning anything for this action. But your reducer should always return something. Instead of break; you should probably have either return state; or return []; depending on exactly how you want to treat the failure case.

查看更多
登录 后发表回答