Vuex 2.0 Dispatch与Commit

imc*_*ngy 40 javascript vue.js vuex

有人可以解释你何时使用派遣与提交?

我理解提交会触发变异,并且调度会触发操作.

但是,不是派遣也是一种行动吗?

Man*_*ani 99

正如你所说,$dispatch触发一个动作,并commit触发一个变异.以下是如何使用这些概念:

您始终使用$dispatch路径/组件中的方法.$dispatch向vuex商店发送消息以执行某些操作.可以在当前刻度之后的任何时间执行操作,以便不影响您的前端性能.

您永远不会commit来自任何组件/路线.它在动作中完成,并且在您有一些要提交的数据时才执行.原因:提交是同步的,可能会冻结您的前端,直到完成为止.

让我们考虑一下这种情况:如果你必须从服务器获取一些json数据.在这种情况下,您需要异步执行此操作,以便您的用户界面暂时不会响应/冻结.所以,你只需要$dispatch一个动作,并期望以后再做.您的操作将执行此任务,从服务器加载数据并稍后更新您的状态.

如果您需要知道某个操作何时完成,那么您可以在此之前显示一个ajax微调器,您可以返回一个Promise,如下所述(例如:加载当前用户):

以下是定义"loadCurrentUser"操作的方法:

actions: {
    loadCurrentUser(context) {
        // Return a promise so that calling method may show an AJAX spinner gif till this is done
        return new Promise((resolve, reject) => {
            // Load data from server
            // Note: you cannot commit here, the data is not available yet
            this.$http.get("/api/current-user").then(response => {
                // The data is available now. Finally we can commit something
                context.commit("saveCurrentUser", response.body)  // ref: vue-resource docs
                // Now resolve the promise
                resolve()
            }, response => {
                // error in loading data
                reject()
            })
        })
    },
    // More actions
}
Run Code Online (Sandbox Code Playgroud)

在您的突变处理程序中,您执行源自操作的所有提交.以下是定义"saveCurrentUser"提交的方法:

mutations: {
    saveCurrentUser(state, data) {
        Vue.set(state, "currentUser", data)
    },
    // More commit-handlers (mutations)
}
Run Code Online (Sandbox Code Playgroud)

在您的组件中,当它是created或时mounted,您只需调用如下所示的操作:

mounted: function() {
    // This component just got created. Lets fetch some data here using an action
    // TODO: show ajax spinner before dispatching this action
    this.$store.dispatch("loadCurrentUser").then(response => {
        console.log("Got some data, now lets show something in this component")
        // TODO: stop the ajax spinner, loading is done at this point.
    }, error => {
        console.error("Got nothing from server. Prompt user to check internet connection and try again")
    })
}
Run Code Online (Sandbox Code Playgroud)

如上所示返回承诺完全是可选的,并且每个人都不喜欢设计决策.有关是否返回承诺的详细讨论,您可以阅读此答案下的评论:https://stackoverflow.com/a/40167499/654825

  • 很好的回应!非常彻底的例子. (6认同)
  • 只是为了记录 - 你可以从一个组件提交 - 它应该是同步的(意思是没有ajax).问题不在于锁定前端 - 它是关于混乱的流程(我提交了一个更改,但它还没有 - 哦ajax没有完成..)如果你提交一个不需要的状态值坚持到任何地方,然后从组件中做到这一点很好.这就是我从我的研究中理解 - 更正欢迎. (4认同)