【问题标题】:Vuex - 计算属性“名称”已分配但它没有设置器
【发布时间】:2018-02-16 18:19:57
【问题描述】:

我有一个带有一些表单验证的组件。这是一个多步骤结帐表格。下面的代码是第一步。我想验证用户是否输入了一些文本,将他们的名字存储在全局状态中,然后发送到下一步。我正在使用vee-validate 和 vuex

<template>
<div>
    <div class='field'>
        <label class='label' for='name'>Name</label>
        <div class="control has-icons-right">

            <input name="name" v-model="name" v-validate="'required|alpha'" :class="{'input': true, 'is-danger': errors.has('name') }" type="text" placeholder="First and Last">
            <span class="icon is-small is-right" v-if="errors.has('name')">
                <i class="fa fa-warning"></i>
            </span>
        </div>
        <p class="help is-danger" v-show="errors.has('name')">{{ errors.first('name') }}</p>

    </div>
    <div class="field pull-right">
        <button class="button is-medium is-primary" type="submit" @click.prevent="nextStep">Next Step</button>
    </div>
</div>
</template>

<script>
export default {
    methods: {
        nextStep(){
            var self = this;

            // from baianat/vee-validate
            this.$validator.validateAll().then((result) => {
                if (result) {
                    this.$store.dispatch('addContactInfoForOrder', self);
                    this.$store.dispatch('goToNextStep');
                    return;
                }
            });
        }
    },
    computed: {
        name: function(){
            return this.$store.state.name;
        }
    }
}
</script>

我有一个用于处理订单状态和记录名称的商店。最终我想将所有信息从多步表单发送到服务器。

export default {
  state: {
    name: '',
  },

  mutations: {
    UPDATE_ORDER_CONTACT(state, payload){
      state.name = payload.name;

    }
  },

  actions: {
    addContactInfoForOrder({commit}, payload) {
      commit('UPDATE_ORDER_CONTACT', payload);
    }
  }
}

当我运行此代码时,我收到一个错误 Computed property "name" was assigned to but it has no setter.

如何将 name 字段的值绑定到全局状态?我希望这是持久的,这样即使用户返回一步(单击“下一步”后),他们也会看到他们在此步骤中输入的名称

【问题讨论】:

  • 除了 Roy J 的回答之外,似乎在没有设置器的计算上使用 v-for 也会引发此警告。

标签: vue.js vuejs2 vue-component vuex computed-properties


【解决方案1】:

我遇到了完全相同的错误

计算属性“callRingtatus”已分配给但它没有设置器

这是根据我的场景的示例代码

computed: {

callRingtatus(){
            return this.$store.getters['chat/callState']===2
      }

}

我把上面的代码改成如下方式

computed: {

callRingtatus(){
       return this.$store.state.chat.callState===2
    }
}

从 vuex 存储状态中获取值,而不是在计算挂钩中获取值

【讨论】:

    【解决方案2】:

    应该是这样的。

    在您的组件

    computed: {
            ...mapGetters({
                    nameFromStore: 'name'
                }),
            name: {
               get(){
                 return this.nameFromStore
               },
               set(newName){
                 return newName
               } 
            }
        }
    

    在您的商店

    export const store = new Vuex.Store({
             state:{
                 name : "Stackoverflow"
             },
             getters: {
                     name: (state) => {
                         return state.name;
                     }
             }
    }
    

    【讨论】:

    • 很抱歉恢复了您的旧答案,但为什么在这种情况下使用吸气剂?为什么不从 mapState 返回 this.nameFromStore ?显然它也同样有效。
    • @Jake 对于这个给出的例子,你说的是对的。但是,当您想操作存储中保存的数据时,您可以在 getter 中执行此操作,但如果您直接使用 this.nameFromStore,则无法操作数据。
    • 感谢您的澄清 :)
    • @Jake 没问题!
    【解决方案3】:

    对我来说它正在改变。

    this.name = response.data;
    

    计算返回的结果是这样的;

    this.$store.state.name = response.data;
    

    【讨论】:

      【解决方案4】:

      如果您要使用 v-model 进行计算,则需要 setter。无论您希望它对更新后的值做什么(可能将其写入$store,考虑到这是您的 getter 从中提取的内容),您都可以在 setter 中执行。

      如果通过表单提交将其写回商店,你不想v-model,你只想设置:value

      如果您想要一个中间状态,它保存在某处但在提交表单之前不会覆盖$store 中的源,您需要创建这样一个数据项。

      【讨论】:

      • 你能提供如何正确创建setter的例子吗?
      • 我帖子的链接有一个例子,this other answer还有一个例子
      猜你喜欢
      • 2021-03-17
      • 2019-05-21
      • 2018-05-07
      • 2018-12-14
      • 2020-10-04
      • 2018-11-02
      • 2018-09-26
      • 2020-11-07
      • 2020-10-23
      相关资源
      最近更新 更多