【Vue.js】Vuexを使ったとき、フォームでv-modelを使うと不具合が出る問題の対処


はじめに

Vuexを使って状態管理すると、フォーム入力でv-modelを使うと、
「ちょっと!勝手にstate変えずにちゃんとmutation通してくれるかな
と怒られる問題があります。

自分はこれに対してどうするのがベストか分からず、試行錯誤を繰り返していました。

そんな時に、手間がかからずラクな方法こちらのブログで発見したので、メモしておきます。

環境

OS: macOS Catalina 10.15.3
Vue: 2.6.10
vuex: 3.1.2

前提

ユーザー情報を入力するフォームがあったとします。

今回はシンプルな例にするため、そのユーザー情報の中でもnameを入力する<input>タグを例にします。

v-modelを使った場合

sample.vue
<template>
<!-- 略 -->
  <input v-model="user.name" >
<!-- 略 -->
</template>

シンプルにこれでOKです。

が、Vuexを使ってこのuserの情報を管理している場合は冒頭の
「ちょっと!勝手にstate変えずにちゃんとmutation通してくれるかな
と怒られる問題が発生します。

これを大した手間をかけずに解決する方法が以下です。

改善後

<input>タグ内

sample.vue
<template>
<!-- 略 -->
  <input
    :value="user.name"
    @input="updateUser($event, 'name')"
  >
<!-- 略 -->
</template>

ここで<input>タグ内のinputイベントで次のupdateUserメソッドが発火、このときのDOMイベントが$eventに入ります。

<input>タグのあるコンポーネントのmethods

sample.vue
<script>
//略
  export default {
//略
    methods: {
      updateUser(event, key_name) {
        this.$store.commit('updateUserState', { 
      value: event.target.value, key_name });
      }
    }
  }
//略
</script>

先程のDOMイベントから入力された文字列valueを抜き出し、key-nameと共に以下Vuexストア内mutationsで定義されたupdateUserState()の引数として渡します。

Vuexストア内

store.js
export default ({
//略
  mutations: {
    updateUserState (state, { value, key_name }) {
      state.user[key_name] = value;
    }
  }
//略
})

最後に、このupdateUserState()でストアのuserの値を変更し、ストア内と<input>タグ内に入力された文字列が同じになります。

以上です!
使い回しやすいコードで超助かりました

おわりに

最後まで読んで頂きありがとうございました

どなたかの参考になれば幸いです

参考にさせて頂いたサイト(いつもありがとうございます)