Подтвердить что ты не робот

Можете ли вы использовать localStorage в исходном состоянии Redux?

Например...

export const user = (state = {
  id: localStorage.getItem('id'),
  name: localStorage.getItem('name'),
  loggedInAt: null
}, action) => {
    case types.LOGIN:
      localStorage.setItem('name', action.payload.user.name);
      localStorage.setItem('id', action.payload.user.id);
      return { ...state, ...action.payload.user }

    default:
      return {  ...state, loggedInAt: Date.now() }
}

Что уменьшенная версия того, что я делаю, по умолчанию возвращает состояние из localStorage, как и ожидалось. Однако состояние моего приложения на самом деле пустое после обновления страницы.

4b9b3361

Ответ 1

Redux createStore Второй параметр предназначен для инициализации магазина:

createStore(reducer, [initialState], [enhancer])

Итак, вы можете сделать что-то вроде этого:

const initialState = {
  id: localStorage.getItem('id'),
  name: localStorage.getItem('name'),
  loggedInAt: null
};

const store = createStore(mainReducer, initialState);

Так как редукторы должны быть чистыми функциями, то есть без побочных эффектов, а localStorage.setItem является побочным эффектом, который, безусловно, повредит тестированию, вам следует избегать сохранения на localStorage в редукторе. Вместо этого вы можете:

store.subscribe(() => {
    const { id, name } = store.getState();

    localStorage.setItem('name', name);
    localStorage.setItem('id', id);
});

Это будет происходить всякий раз, когда изменяется состояние, поэтому оно может повлиять на производительность.

Другой вариант - сохранить состояние только тогда, когда страница закрыта (подсчет обновлений) с помощью onBeforeUnload:

window.onbeforeunload = () => {
    const { id, name } = store.getState();

    localStorage.setItem('name', name);
    localStorage.setItem('id', id);
};