LoginSignup
76
54

More than 3 years have passed since last update.

Vuex のmapStateなどの書き方決定版!

Last updated at Posted at 2018-12-10

はじめに

VuexのmapStatemapActionsって便利ですけど、色々な書き方があってややこしいですね。

例えば、以下のケースでそれぞれ書き方が変わってきます。

  • ヘルパー以外のプロパティも定義したい場合
  • モジュールから値を取ってきたい場合
  • 値にエイリアス(別名)をつけたい場合
  • 値に何らかの処理をほどこしたい場合

本記事では「この2パターンだけ覚えていればOK」という書き方をご紹介します。

前提

前提として、userというモジュールに、idageというステートが定義されているとします。

store/index.js
const user = {
  state: {
    id: ''
    age: null
  },
  namespaced: true,
}

また、必要なヘルパーはインポートされているとします。

pages/index.vue
<script>
import { mapState, mapGetters, mapMutations, mapActions } from 'vuex'

書き方1(簡易型)

まずは、よく使う簡易的な書き方から。

ストアの値をそのまま使うだけの場合は、以下のように書けます。

pages/index.vue
  computed: {
    ...mapState('user', [
      'id', 
      'age'
    ]),

    // この後にもちゃんと関数を定義できる

  },

これにより、userモジュールのid, agethis.id, this.age で取得できます。

参照先がモジュールじゃない場合は第1引数を省略するだけです。

モジュールじゃない場合
  ...mapState([
    'some', 
    'states'
  ]),

他の3つのヘルパーも同様に書けるので省略します。
(ただしmapMutationsmapActionsは、computedではなくmethods内に定義します)

書き方2(万能型)

こちらはあらゆるケースで使える書き方です。
(ただエイリアスや値の加工が不要な場合は、書き方1より冗長になります)

  computed: {
    ...mapState('user', {
      userId: 'id',
      isAdult: function(state) {
        return state.age > 19, // 成人かどうかを Boolean で返す
      },
    }),

    // この後にもちゃんと関数を定義できる
  },

書き方1と異なるのは、引数に配列ではなくオブジェクトを渡している点です。
そのオブジェクトには、

エイリアス名: '取得したいキー名' あるいは
エイリアス名: function (MapGetters 以外)

という形のプロパティを定義します。
(function を渡すやり方については下で補足解説します)

:point_up:のコードでは、

  • this.userIdで user のidが取得できる
  • this.isAdultで「年齢が20歳以上かどうか」が取得できる

ようになっています。

補足(function を渡す書き方)

mapState, mapMutations, mapActionsでは、プロパティに function を渡すことで値の加工や処理の追加が行えます。

  • mapStateの場合はstateを引数とし、加工した値を戻り値とします。

  • mapMutations, mapActionsの場合はそれぞれcommit, dispatchを引数とし、行いたい処理を記述します。実例を置いておきます。

※「値を加工するなら getters に書けばいいのでは?」と思われるかもしれませんが、例えば一つのページでしか使わないような値の場合、こうすることで getters の肥大化が避けられます。

その他の注意点

  • ヘルパーを書く場所は、

    • mapState, mapGetterscomputed
    • mapMutations, mapActionsmethods
  • 参照先がモジュールではない場合は第1引数を省略する

  • モジュールがネストしている場合は、モジュール名をスラッシュで区切って指定する。例:”user/photo”

参考

Vuex:mapStateの書き方8パターン+11サンプルコード

76
54
1

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
76
54