web-dev-qa-db-ja.com

Reduxの初期状態でlocalStorageを使用できますか、それとも使用すべきですか?

例えば...

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から状態を期待どおりに返します。ただし、ページを更新すると、アプリケーションの状態は実際には空白になります。

24
Ewan Valentine

Redux createStore 2番目のパラメーターは、ストアの初期化を目的としています。

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);
});

これは状態が変化するたびに発生するため、パフォーマンスに影響を与える可能性があります。

もう1つのオプションは、onBeforeUnloadを使用してページが閉じられたとき(カウントの更新)にのみ状態を保存することです。

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

    localStorage.setItem('name', name);
    localStorage.setItem('id', id);
};
39
Ori Drori