LoginSignup
16
14

More than 5 years have passed since last update.

Vuexのstateを手短く初期化したいがうまく行かなかったお話し

Posted at

環境

Vue 2.x, Vuex 2.3.1

課題

stateを初期化したい

// こんなstateがあるとして
const defaultState = {
  foo: 0,
  bar: 0
}

const mutations = {
  // 値を変えるぞ
  ['DO_SOMETHING'] (state) {
    state.foo = 99
    state.bar = 999
  },
  // お行儀よく初期化するぞ
  ['STATE_INIT'] (state) {
  state.foo = 0
  state.bar = 0
  }
}

export default {
  state: defaultState,
}

storeを変更しよう

store.commit('DO_SOMETHING') // OK

storeをリセットしよう

store.commit('STATE_INIT') // OK

ではSTATE_INITを短くしてみよう

['STATE_INIT'] (state) {
  state = defaultState
}

defaultStateは参照渡しだから、DO_SOMETHING で汚染されてるので初期化にはならない。これは分かってる。

ならば参照渡しを切って完全コピーしたものにしよう

[STATE_INIT] (state) {
  state = JSON.parse(JSON.stringify(defaultState))
}

export default {
  state: JSON.parse(JSON.stringify(defaultState)),
}

結果はダメ。

lodashのcloneDeepはどうだ?

[STATE_INIT] (state) {
  state = cloneDeep(defaultState)
}

export default {
  state: cloneDeep(defaultState),
}

やっばりだめ

結論

// ここは Object.assign なら初期化できる!!!!!!
[STATE_INIT] (state) {
  Object.assign(state, defaultState)
}

// ここは JSON.stringify または cloneDeep どっちでもいい
export default {
  state: JSON.parse(JSON.stringify(defaultState)),
}

これでめでたく初期化できた。キモは Object.assign

16
14
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
16
14