With Redux-Persist, how do I set the initial state of my reducer to be what is stored in local storage?

254 views Asked by At

I'm using Ionic 7, React 18, and Redux-Toolkit and Redux-Persist. I would like to persist one of my states (cart) to local storage. I have set up my cartSlice as below

interface CartState {
  [key: string]: OrderItem[];
}

const initialState: CartState = {};

const cartSlice = createSlice({
  name: "cart",
  initialState,
  reducers: {
    ...
    },

    clearCart: (state) => {
      ...
    },
  },
});

export const {
  addToCart,
  clearCart,
} = cartSlice.actions;

export default cartSlice.reducer;

and set up my root persist reducer as below

const rootPersistConfig = {
  key: 'root',
  storage: storage,
  blacklist: ['auth'],
  stateReconciler: autoMergeLevel2
};

const authPersistConfig = {
  key: 'auth',
  storage: sessionStorage,
}

const rootReducer = combineReducers({
  auth: persistReducer(authPersistConfig, authReducer),
  cart: cartReducer,
})

const persistedReducer = persistReducer(rootPersistConfig, rootReducer);

export default persistedReducer;

in which I load this into my store like below

export const store = configureStore({
  reducer: persistedReducer, // rootReducer,
  devTools: import.meta.env.VITE_NODE_ENV !== "production",
});

What I'm not clear about is how to set my initial state to be local storage, assuming there is already something there. Every time I load my app, my initial state is reset to "{}", due to how I set it in my slice, but I can't figure out how to tell my state that the initial state can be loaded from local storage, if the state is already there.

2

There are 2 answers

0
Drew Reese On BEST ANSWER

Ensure that you are following all of the setup/configuration steps.

const rootPersistConfig = {
  key: "root",
  storage: storage,
  blacklist: ["auth"],
  stateReconciler: autoMergeLevel2
};

const authPersistConfig = {
  key: "auth",
  storage: sessionStorage
};

const persistedAuthReducer = persistReducer(authPersistConfig, authReducer);

const rootReducer = combineReducers({
  auth: persistedAuthReducer,
  cart: cartReducer
});

const persistedReducer = persistReducer(rootPersistConfig, rootReducer);

const store = configureStore({
  reducer: persistedReducer // rootReducer,
  devTools: import.meta.env.VITE_NODE_ENV !== "production",
});

const persistor = persistStore(store); // <-- persist store

...

<Provider store={store}>
  <PersistGate persistor={persistor}> // <-- persist gate
    ....
  </PersistGate>
</Provider>

Edit with-redux-persist-how-do-i-set-the-initial-state-of-my-reducer-to-be-what-is-s

1
rain developer On

You can use the stateReconciler option in the rootPersistConfig configuration object to ensure that the initial state of your cart is populated from local storage if it is available. The stateReconciler function is in charge of combining the persisted state from local storage with the reducer's default initial state.

The following is an example of how to use the stateReconciler function:

const stateReconciler = (storeState, persistedState) => {
  // Check if there's cart data in local storage
  if (persistedState.cart) {
    // Merge the persisted cart data with the default initial state
    return {
      ...storeState,
      cart: persistedState.cart,
    };
  }

  // If no cart data exists in local storage, use the default initial state
  return storeState;
};

Also include the following function in your rootPersistConfig configuration:

const rootPersistConfig = {
  key: 'root',
  storage: storage,
  blacklist: ['auth'],
  stateReconciler: stateReconciler,
};

The initial state of your cart will be populated from local storage if available with this setup, ensuring that the cart remains persistent between page reloads or app restarts.