If have a state of objects payload:
export const initialState = {
payload: {
firstName: 'Mick',
lastName: 'Andri',
phoneNumber: '651-332-5675',
electronicMailAddress: '[email protected]',
addressLine1: '27 Crest Ave',
addressLine2: '',
cityName: 'San Jose',
stateCode: 'CA',
zipCode: '92122',
},
};
and to load this state it in some way I using immer:
const SettingsReducer = (state = initialState, action) =>
produce(state, (draft) => {
switch (action.type) {
case actionTypes.LOAD_SETTINGS_INFO:
draft.payload = action.payload;
break;
}
});
export default SettingsReducer;
If we were to do this the usual way with JavaScripts object and array spread syntax, our state reducer might look like below, this is just an example:
draft.payload = action.payload;
case 'UPDATE_SETTINGS_INFO':
return {
...state,
payload: [...state.payload, action.payload],
};
In my case:
I getting all fields through the react hook form and trying to update my state. I need to update the state without losing the whole data.
The code below works but deletes the rest of the data from the state.
case actionTypes.UPDATE_SETTINGS_INFO:
draft.payload = action.payload;
break;
I need to update half of the state at one time.
What is the best way to clone the state without losing the whole data?
First, I would recommend not having a
state.payloadfield. "Payload" is normally used to describe "the contents of an action object", and as a term it really doesn't make sense for state in a reducer.Second, it sounds like what you're trying to do here is merge two objects together, such that fields in the second override fields in the first. If we were doing an immutable update (and assuming that
stateitself is the original data), we could doreturn {...state, ...action.payload}.With Immer, you can "mutate" the object directly:
If there's multiple fields you want to update at once, and
action.payloadwill contain some or all of the fields in the original state, you can do this with Immer:Finally, I'd specifically recommend using our official Redux Toolkit package, which already uses Immer inside of its
createSliceAPI:See the Redux tutorials for more details:
https://redux.js.org/tutorials/index