【Vuex 源码学习】第七篇 - Vuex 对 State 状态的处理
一,前言
上一篇,主要介绍了 Vuex 模块安装的实现,针对 action、mutation、getter 的收集与处理,主要涉及以下几个点:
Vuex 模块安装的逻辑;
Vuex 代码优化;
Vuex 模块安装的实现;
Vuex 初始化流程梳理;
本篇,继续介绍 Vuex 模块相关概念:Vuex 对 State 状态的处理;
二,State 状态的处理
接下来,需要将所有子模块的状态,合并到对应的父模块中;
子模块的 path.length > 0
,需要将当前子模块的 State 状态,挂载到它的父模块上;
通过 Vue.set
声明响应式数据
为什么不直接赋值?
因为 Vuex 要求模块是可以动态进行添加的,即 Vuex 能够动态的添加模块
我们希望动态添加的模块也是响应式的数据,因为刚开始的对象没有,后来又有了,需要使用 Vue.set
API 为对象新增加一个不存在的属性,等下再注册新模块时,就不同再去变成响应式的了;
Vue.set
也可以直接为对象添加值:如果对象本身不是响应式的,那么 Vue.set
就相当于直接为对象添加了属性, Vue.set
既能解决响应式问题,也能为普通对象进行赋值;
如何找父亲?
将子模块状态定义到父模块上:
从根模块的状态开始找,返回当前模块所属的父模块 parent;
将当前模块的 State 状态设置到父模块 parent 的 path[path.length-1] 属性中;
即将所有状态都放到 rootState 上
首次,返回 rootState,相当于为根加上 a 和 b 的 state
非首次,找到 a,将 c 定义到 a 的状态中;
打印合并后状态 state(包含全部模块的状态):
根上有 a,b 的状态,a 上有 c 的状态
备注:循环处理当前模块的子模块时,完成 path 的拼接操作;
三,resetStoreVM 方法实现
有了 state 和 getters,需要创建一个实例
创建 resetStoreVM 方法:
传入 this:this 中包含 _wrapperGetters 全部的 getter 方法;
传入 state:rootState 根状态,包含全部的状态;
和之前的实现相同:将 State 状态和 getters 都定义在当前 vm 实例上;
借助一个 Vue 实例,将 state 定义到 data 中,计算属性通过 getters 生成;
在 src/vuex/store.js 中,创建 resetStoreVM 方法:
测试:
通过类型,找到对应的数组,数组内存放着所有方法,循环执行即可
四,操作的执行逻辑
commit、dispatch 找到对应的数组并依次执行
这里使用到了发布订阅模式,先将所有模块中的 mutation 和 action 放到两个数组中,调用时到当前对象中找到对应的数组并依次执行
这样,数据是如何放入,如何执行的就清晰了,后续进行命名空间的处理;
五,结尾
本篇,主要介绍了 Vuex 初始化时对 State 状态的处理,主要涉及以下几个点:
State 状态的处理;
resetStoreVM 方法实现;
操作的执行逻辑;
下一篇,继续介绍 Vuex 模块相关概念:namespaced 命名空间的实现;
评论