005-vuex是如何实现严格模式的?

首先介绍一下什么是vuex的严格模式?
在严格模式下,无论何时发生了状态变更且不是由 mutation 函数引起的,将会抛出错误。这能保证所有的状态变更都能被调试工具跟踪到。也就说想要改变状态,必须要使用mutation函数。

那么vuex是如何实现严格模式的呢?
一、首先要开启严格模式。

const store = new Vuex.Store({
  // ...
  strict: true
})

用户实例化Store的时候传入strict为true就开启了严格模式

二、接收参数

const {
      strict = false
    } = options

// strict mode
    this.strict = strict

 // enable strict mode for new vm
  if (store.strict) {
    enableStrictMode(store)
  }

接收参数,如果strict就调用enableStrictMode方法

三、enableStrictMode实现

function enableStrictMode (store) {
  store._vm.$watch(function () { return this._data.$$state }, () => {
    if (process.env.NODE_ENV !== 'production') {
      assert(store._committing, `do not mutate vuex store state outside mutation handlers.`)
    }
  }, { deep: true, sync: true })
}
// util.js里提供的
export function assert (condition, msg) {
  if (!condition) throw new Error(`[vuex] ${msg}`)
}

这个方法主要有两点,一个是$watch,这个功能是vue提供的,另一个是assert,总结分析就是改变this._data.$$state的时候,store._committing必须为true,否则就警报。接下去就分析store._committing。

四、store._committing分析

this._committing = false

_withCommit (fn) {
    const committing = this._committing
    this._committing = true
    fn()
    this._committing = committing
  }

刚开始的时候,这个变量设置为false,如果要改变数据包装一个_withCommit方法,执行方法之前,将this._committing设置true,执行完了之后改回false.

五、使用_withCommit封装函数

store._withCommit(() => {
  Vue.set(parentState, moduleName, module.state)
})

源码里其他地方也用了_withCommit。

所以vuex实现严格模式的原理就是改变状态的时候,标记一个变量是否为true。

你可能感兴趣的:(005-vuex是如何实现严格模式的?)