vuex中直接修改state 与 用dispatch/commit来修改state的差异

·  阅读 1896

背景

当我们使用vuex进行状态管理的时候,我们总是会看到一句话更改Vuex 的store 中的状态的唯一方法是提交mutation,但是我们不提交mutation就没法修改state的值的了,其实是不对的,我们也可以通过下面的方法进行state值的修改。

this.$store.state.aaa = xxx
复制代码

并且我们发现直接修改state时,store中的state能够改变,并且是响应式的,并没有报错。但是为啥文档还要强调我们修改state的唯一方式是提交mutation呢?

当我们将vuex的模式改成严格模式的时候,我们在通过直接修改state的方式修改状态的时候,控制台会报错。

官方文档中也进行了描述

开启严格模式,仅需在创建 store 的时候传入 strict: true; 在严格模式下,无论何时发生了状态变更且不是由 mutation 函数引起的,将会抛出错误。这能保证所有的状态变更都能被调试工具跟踪到。

解答

使用commit提交状态修改是为了配合开发者工具使用,使得状态更好的被最终,保存状态快照,实现时间漫游/回滚之类的操作。

其实官方文档有很好的解释

这个简单的约定能够让你的意图更加明显,这样你在阅读代码的时候能更容易地解读应用内部的状态改变。此外,这样也让我们有机会去实现一些能记录每次状态改变,保存状态快照的调试工具。有了它,我们甚至可以实现如时间穿梭般的调试体验。

源码分析

首先我们看看当我们开启严格模式后,vuex是怎么处理的

开启严格模式后我们将执行enableStrictMode函数,这个函数内部通过watch来判断state的更新,当state变化后,如果是非生产模式,判断store._committing的值来是否抛错。

我们发现store._committing的默认值是false,那么默认情况下,当state改变后必然是会抛错的。

我们接下来看看通过commit来修改state的逻辑

我们发现,当通过commit来进行状态修改的时候,会将_committing设置为true,这样就不会进行报错了。

结语

根据上面的分析,开发模式的时候,我们在使用vuex的时候最好设置成严格模式,修改state的时候我们不要直接修改,而是通过commit来提交。主要是为了状态能够很好的跟踪,开发者工具更好的处理状态变化,更好的调试体验。

分类:
前端
标签: