7
votes

If I have a Vuex module which is namespaced, how to create the getters and setters for the states in that module when using these state in Vue components?

// My component
new Vue({

 computed: {

   // How do I add setters also below????

   ...mapState('nameSpacedModA', {
       a : state => state.a,
       // ...
   },


   // Following will only add getters..
   // How to add setter ??? 

   ...mapGetters('nameSpacedModA', {
         a: 'a', 
         b: 'b' //, ...
    }
}

I am binding 'a' to a text input on a form using v-model and then when I edit the control value, Vue is giving error:

[Vue warn]: Computed property "a" was assigned to but it has no setter.

How to solve this?

2

2 Answers

8
votes

If you want do do 2 ways binding, you need to defined both getter and setter in computed properties. (Don't forget to define mutation updateA)

<input v-model="a">
// ...
computed: {
  a: {
    get () {
      return this.$store.state.a
    },
    set (value) {
      this.$store.commit('updateA', value)
    }
  }
}

Another option is using mapFields

0
votes

I found another way using Vuex mapStates and mapActions helpers. This is slightly more verbose. So using the v-model binding approach is more better.

// BTW: If you use the approach as suggested by ittus then you will use the v-model binding like below:

<input v-model="a" />

// Using the other approach that I used you will have to do two-way binding as below:

<input :value="a" @input="updateA" />

If you want to use the v-model binding then the code will be something like below:

// Vuex store 
....
modules: {ModuleA, ...}


// ModuleA of store
export default {
  namespaced: true,
  states: {
    a: '',
  },

  mutations: {
     updateA: (state, value) => state.a = value
  },

  actions: {
    updateA(context, value) { context.commit('updateA', value) }
  }
}

// Then in your Component you will bind this Vuex module state as below
new Vue({
  store,

  computed: {
     a: {
         get() { this.$store.state.ModuleA.a; }
         set(value) {this.updateA(value);}
      },

  },

  methods: {
    ...mapActions('MyModule', [ updateA ]),
  }
})