【问题标题】:vuexjs getter with argument带参数的 vuexjs getter
【发布时间】:2017-05-21 02:06:36
【问题描述】:

有没有办法将参数传递给vuexstore的getter? 比如:

new Vuex.Store({
  getters: {
    someMethod(arg){
       // return data from store with query on args
    }
  }
})

这样我就可以在组件中使用

<template>
    <div>
        <p>{{someMethod(this.id)}}</p>
    </div>
</template>
<script lang="ts">
    import { mapGetters } from "vuex"

    export default {
        props: ['id'],
        computed: mapGetters(['someMethod'])
        }
    }
</script>

但在 vuex 中,第一个参数是 state,第二个是其他 getters。有可能吗?

【问题讨论】:

    标签: javascript vue.js vuejs2 vuex


    【解决方案1】:

    一种方法可以是:

    new Vuex.Store({
      getters: {
        someMethod(state){
          var self = this;
           return function (args) {
              // return data from store with query on args and self as this
           };       
        }
      }
    })
    

    但是,getter 不接受参数,原因在此 thread 中进行了解释:

    命名约定有点混乱,getter 表示可以以任何形式检索状态,但实际上它们是 reducer。

    也许我们应该让 reducer 成为纯方法。可用于过滤、映射等。

    getter 然后可以被赋予任何上下文。与计算类似,但您现在可以将计算道具与 vuex 选项中的 getter 组合起来。这有助于组件的结构。

    编辑:

    实现相同目的的更好方法是使用nivram80 的答案中详述的 ES6 箭头,使用 method style getters 可以通过从 getter 返回函数来传递参数:

    new Vuex.Store({
      getters: {
        someMethod: (state) => (id) => {
            return state.things.find(thing => thing.id === id)
          }
        };       
      }
    })
    

    【讨论】:

    • getter/computed 变量的主要目的是缓存结果。你知道它是否适用(以及如何)在这种特殊情况下?塔。
    • @xpuu 看看这个问题对缓存的简短分析:stackoverflow.com/questions/44575886/…
    【解决方案2】:

    ES6 箭头函数在这里也可以很好地工作。例如,清酒,假设您正在商店中寻找特定的“东西”。

    new Vuex.Store({
      getters: {
        someMethod: (state) => (id) => {
          return state.things.find(thing => thing.id === id)
        }
      },
    })
    

    这是另一个通过Vuex documentation的例子

    【讨论】:

    • 完美。我将这种技术用于非常相似的目的。而不是这个:let something = this.$store.state.things &amp;&amp; this.$store.state.things.thing ? this.$store.state.things.thing : null,我现在可以做let something = this.$store.getters.getThings('thing')
    • 这应该是公认的答案,因为 a) 它回答了问题,并且 b) 它不提倡不良做法。接受的答案很糟糕,应该删除。
    • 当我这样做时,我得到了错误:不要在突变处理程序之外改变 vuex 存储状态。我知道这行得通我以前做过,但现在我坚持下去了:/
    【解决方案3】:

    您可以通过返回函数将参数传递给 getter。这在您想查询存储中的数组时特别有用:

    getters: {
      // ...
      getTodoById: (state) => (id) => {
        return state.todos.find(todo => todo.id === id)
      }
    }
    

    在你的 vue 组件中:

    store.getters.getTodoById(2) // -> { id: 2, text: '...', done: false }
    

    请注意,通过方法访问的 getter 将在您每次调用它们时运行,并且结果不会被缓存。

    以上答案摘自Vue官方文档:https://vuex.vuejs.org/guide/getters.html#method-style-access

    【讨论】:

      【解决方案4】:

      你可以像这样使用 MapGetters 助手,一旦定义了 store getter:

      new Vuex.Store({
        getters: {
          someMethod(state){
             return (value) => {
                return value;
             }
          }
        }
      })
      

      然后像这样从一个组件调用getter:

      <script>
          import { mapGetters } from "vuex"
      
          export default {
           computed: {
           ...mapGetters(['someMethod'])
           },
           mounted() {
             console.log(this.someMethod('hello world')); // then logs "hello world"
           }       
      }
      </script>
      

      【讨论】:

        【解决方案5】:

        我不认为这就是 vuex.getter 的本意。

        首先,正如您在上述所有示例中所见,getter 可以映射为仅计算对象

        <script>
            import { mapGetters } from "vuex"
        
            export default {
             computed: {
             ...mapGetters(['someGetter'])
             },
             mounted() {
               console.log(this.someGetter); // a computed is not a method.
             }       
        }
        </script>
        

        如果你需要它来接收参数,你想要的是一个方法,而不是一个计算的。

        我建议您改用 store.action:

        new Vuex.Store({
          actions: {
            someMethod({ state }, arg){
               // do something with state.someValue and the arg
               return someTransformationOfYourState;
            }
          }
        })
        

        因为动作和突变可以映射为方法。 你可以像这样使用它:

        <script>
            import { mapActions } from "vuex"
        
            export default {
             computed: {
             
             },
             mounted() {
               // now you can use someMethod with args in your component 
               this.someMethod('the arg');
             },
             methods: {
             ...mapActions(['someMethod'])
             },       
        }
        </script>
        

        动作的第一个参数是商店本身,因此您可以从那里访问状态。与 dispatch 和 commit 函数相同。

        注意动作只能接收一个参数(有效负载),因此如果您需要发送更多参数,则必须将它们全部包装在一个对象或数组中

        this.someMethod({ arg1, arg2, ...});
        

        【讨论】:

        猜你喜欢
        • 2020-02-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-05-07
        • 2021-11-05
        • 2017-11-18
        • 2018-04-20
        相关资源
        最近更新 更多