国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > JavaScript > 正文

詳解vuex之store源碼簡單解析

2019-11-19 11:21:01
字體:
來源:轉載
供稿:網友

關于vuex的基礎部分學習于http://www.survivalescaperooms.com/article/163008.htm

使用Vuex的時候,通常會實例化Store類,然后傳入一個對象,包括我們定義好的actions、getters、mutations、state等。store的構造函數:

export class Store { constructor (options = {}) {  // 若window內不存在vue,則重新定義Vue  if (!Vue && typeof window !== 'undefined' && window.Vue) {   install(window.Vue)  }  if (process.env.NODE_ENV !== 'production') {   // 斷言函數,來判斷是否滿足一些條件   // 確保 Vue 的存在   assert(Vue, `must call Vue.use(Vuex) before creating a store instance.`)   // 確保 Promsie 可以使用   assert(typeof Promise !== 'undefined', `vuex requires a Promise polyfill in this browser.`)   assert(this instanceof Store, `store must be called with the new operator.`)  }  // 解構賦值,拿到options里的plugins和strict  const {   plugins = [],   strict = false  } = options  // 創建內部屬性  // 標志一個提交狀態,作用是保證對 Vuex 中 state 的修改只能在 mutation 的回調函數中,而不能在外部隨意修改 state  this._committing = false   // 用來存儲用戶定義的所有的actions  this._actions = Object.create(null)  this._actionSubscribers = []  // 用來存儲用戶定義所有的mutatins  this._mutations = Object.create(null)  // 用來存儲用戶定義的所有getters   this._wrappedGetters = Object.create(null)  // 用來存儲所有的運行時的 modules  this._modules = new ModuleCollection(options)  this._modulesNamespaceMap = Object.create(null)  // 用來存儲所有對 mutation 變化的訂閱者  this._subscribers = []  // 一個 Vue對象的實例,主要是利用 Vue 實例方法 $watch 來觀測變化的  this._watcherVM = new Vue()  // 把Store類的dispatch和commit的方法的this指針指向當前store的實例上  const store = this  const { dispatch, commit } = this  this.dispatch = function boundDispatch (type, payload) {   return dispatch.call(store, type, payload)  }  this.commit = function boundCommit (type, payload, options) {   return commit.call(store, type, payload, options)  }  // 是否開啟嚴格模式  this.strict = strict  const state = this._modules.root.state  // Vuex的初始化的核心,其中,installModule方法是把我們通過options傳入的各種屬性模塊注冊和安裝;  // resetStoreVM 方法是初始化 store._vm,觀測 state 和 getters 的變化;最后是應用傳入的插件。  installModule(this, state, [], this._modules.root)  resetStoreVM(this, state)  plugins.forEach(plugin => plugin(this))  const useDevtools = options.devtools !== undefined ? options.devtools : Vue.config.devtools  if (useDevtools) {   devtoolPlugin(this)  } }

Vuex本身是單一狀態樹,應用的所有狀態都包含在一個大對象內,隨著我們應用規模的不斷增長,這個Store變得非常臃腫。為了解決這個問題,Vuex允許我們把store分模塊。每一個模塊包含各自的state、mutations、actions和getters,甚至還可以嵌套模塊。

接下來看installModule方法:

function installModule (store, rootState, path, module, hot) { // 通過path數組的長度判斷是否為根 const isRoot = !path.length const namespace = store._modules.getNamespace(path) // register in namespace map if (module.namespaced) {  store._modulesNamespaceMap[namespace] = module } // 第一次調用時,path為空,不進入if // 遞歸調用installModule安裝子模塊時,將執行該代碼塊 if (!isRoot && !hot) {  const parentState = getNestedState(rootState, path.slice(0, -1))  // 模塊名  const moduleName = path[path.length - 1]  // 把當前模塊的state添加到parentState中。具體解析見下  store._withCommit(() => {   Vue.set(parentState, moduleName, module.state)  }) } const local = module.context = makeLocalContext(store, namespace, path) // 對mutations、actions、getters進行注冊 module.forEachMutation((mutation, key) => {  const namespacedType = namespace + key  registerMutation(store, namespacedType, mutation, local) }) module.forEachAction((action, key) => {  const type = action.root ? key : namespace + key  const handler = action.handler || action  registerAction(store, type, handler, local) }) module.forEachGetter((getter, key) => {  const namespacedType = namespace + key  registerGetter(store, namespacedType, getter, local) }) // 遍歷modules,遞歸調用installModule安裝子模塊 module.forEachChild((child, key) => {  installModule(store, rootState, path.concat(key), child, hot) })}store的_withCommit方法定義是這樣的: _withCommit (fn) {  const committing = this._committing  this._committing = true  fn()  this._committing = committing }

Vuex中所有對state的修改都會用_withCommit函數包裝,保證在同步修改state的過程中this._committing的值始終為true。這樣當我們觀測 state的變化時,如果this._committing的值不為true,則能檢查到這個狀態修改是有問題的。

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持武林網。

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 门头沟区| 建德市| 东莞市| 清河县| 临漳县| 阳东县| 益阳市| 景泰县| 台东县| 莎车县| 丁青县| 万州区| 雷州市| 法库县| 兴隆县| 南丹县| 兰溪市| 盐亭县| 保定市| 赣榆县| 理塘县| 清苑县| 集安市| 屯昌县| 德庆县| 扶沟县| 锡林浩特市| 鄯善县| 永平县| 皋兰县| 库车县| 将乐县| 正镶白旗| 乌苏市| 藁城市| 梅州市| 从化市| 阿克陶县| 漳平市| 泊头市| 阳东县|