Vuexのモジュール分割について
Vuexでストアを管理していると、アプリケーションが大きくなるにつれてストアが肥大化し、見通しが悪くなる問題が起こります。
それを回避するためにストアを分割できるようになっています。例えばアプリケーションの機能ごとやページごとにストアを分割していれば、コードの見通しがよくなりますし、プロジェクトメンバーで共同で作業しやすくなります。
以下にストアを分割する方法を記載します。
// ストア側 import Vue from "vue"; import Vuex from "vuex"; Vue.use(Vuex); const moduleA = { namespaced: true, state: {...}, getters: {...}, mutations: {...}, actions: {...} } const moduleB = { namespaced: true, state: {...}, getters: {...}, mutations: {...}, actions: {...} } export default new Vuex.Store({ modules: { aaa: moduleA, bbb: moduleB } });
これでストア分割完了です。
ポイントは各モジュールを定義するときに、namespacedオプションをtrue
に設定することです。
モジュール分割をすると、同一のミューテーションタイプやアクションタイプが指定できることになります。そのため、どちらか一方を呼び出したときに、同一のタイプはすべて呼び出されることになります。それを避けるために、namespaced
をtrue
にすることで影響範囲を限定することができます。
namespaceを与えたときは以下のように、各モジュールのミューテーションタイプ、アクションタイプを指定して呼び出します。
// コンポーネント側 this.$store.commit('aaa/設定したミューテーションタイプ') this.$store.dispatch('bbb/設定したアクションタイプ') this.$store.getters['ccc/設定したゲッター'] // これはゲッターの例
このようにnamespaceを設定することでモジュールごとのミューテーション、アクション、ゲッターを呼び出せます。
マップヘルパーにnamespaceを登録すればモジュール名を省略して呼び出せます。その場合はヘルパーの第一引数にnamespaceを指定します。
computed: { ...mapMutations("aaa",["設定したミューテーションタイプ"]), this.[設定したミューテーションタイプ] }
ちなみにモジュール分割はネストもできるので、以下のように書くことも可能です。
const moduleA = { namespaced: true, state: {...}, getters: { parentGet: ... }, mutations: {...}, actions: {...}, modules: { page01: { // 親のnamespaceを継承するので、例えばゲッターを指定したいときは親モジュールのゲッターの呼び方と同じでOK(下記★参照) state: {...}, getters: { get: // ゲッターの処理書く }, mutations: {...}, actions: {...}, modules: { namespaced = true layer01: { // namespacedを指定しているので、例えばゲッターを指定したいときは親モジュールから相対パスで指定して呼び出す(下記♦参照) namespaced: true, state: {...}, getters: { get: // ゲッターの処理書く }, mutations: {...}, actions: {...}, } } } } }
★の呼び出し方
...mapGetters("aaa", ["parentGet", "get"]), // マップヘルパー使ったとき this.get // これで子のget呼べる this.$store.getters.parentGet // マップヘルパー使わない場合
♦の呼び出し方
...mapGetters("aaa", ["parentGet", "get", "layer01/get"]), // マップヘルパー使ったとき this['layer01/get'] // これで孫のget呼べる this.$store.getters['form/layerPage/profile'] // マップヘルパー使わない場合は親からの相対パスで呼ぶ
モジュール分割は他にも例えば別モジュールに登録された処理を呼び出したり、ルートに登録されたモジュールを呼べたりするので、公式ドキュメント載せておきます。
参考資料
モジュール | Vuex