0

In React we have a best practice not modify state directly i.e. mutation... It is also important in Redux...

/* initial state */
export const usersStartState = { users: { isLoggedIn: false } }

export default function users(state = usersStartState, action) {
    switch (action.type) {
        case actionTypes.users.IS_LOGGED_IN:
            return Object.assign({}, state,
                state.users.isLoggedIn = true)
        case actionTypes.users.IS_LOGGED_OUT:
            return Object.assign({}, state,
                state.users.isLoggedIn = false)
        default:
            return state
    }
};

The above doesn't work, but can anyone help me how to properly update that nested objects property?

0

2 Answers 2

1

Looks like you're both mutating state and returning a new state object. You're mutating state by saying state.users.isLoggedIn = .., but then returning a new state object by doing return Object.assign(...).

Instead maybe just do

case actionTypes.users.IS_LOGGED_OUT:
  return { ...state, users: { ...state.users, isLoggedIn: false }};

An alternative would be to create a copy of state and modify it instead

// Create new object so we don't mutate state
let newState = {...state, users: {...state.users}; 
// Remember to do this for each nested object or you 
// will still be referencing that piece of the original state
switch (action.type) {
  case actionTypes.users.IS_LOGGED_IN:
    newState.users.isLoggedIn = true; // Make your changes
    return newState; // Return new state
  case actionTypes.users.IS_LOGGED_OUT:
    newState.users.isLoggedIn = true;
    return newState;
  default:
    return state;
}
Sign up to request clarification or add additional context in comments.

3 Comments

I forgot to spread state.users, saw your answer and remembered. Thanks
Thanks Brian, but this case actionTypes.users.IS_LOGGED_IN: return {...state, users: {...state.users, isLoggedIn: true } }; yields {users: isLoggedIn: false users: {isLoggedIn: true}}
That return value doesn't look like a valid format? is that exactly what its returning? Or is it supposed to be {isLoggedIn: false}, ?
1

You can do this

return {...state, users:{...state.users, isLoggedIn : true}}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.