Vuex源碼學習(五)加工後的module

沒有看過moduleCollection那可不行!Vuex源碼學習(四)module與moduleCollectionvue

感謝提出代碼塊和截圖建議的小夥伴

代碼塊和截圖的區別:vuex

  1. 代碼塊部分但願你們按照個人引導一行行認真的讀
  2. 代碼的截圖是但願你們能記住圖中的結構,下面會對總體進行一個分析,而不會一行一行的分析。

可是之後的文章會更偏向於使用代碼塊,但願你們喜歡。緩存

上一章咱們講述了ModuleCollection類的做用,幫助咱們把僞(未加工的)模塊變成真正的模塊,而後把每一個模塊按照父子與兄弟關係連接起來。那麼真正的模塊相比於僞(未加工的)模塊多了哪些能力呢?bash

module提供的方法

這是module暴露出來的全部方法,以及一個屬性。

先看一下constructor

constructor (rawModule, runtime) {
    this.runtime = runtime
    // Store some children item
    // 建立一個容器存放該模塊全部的子模塊
    this._children = Object.create(null)
    // Store the origin module object which passed by programmer
    // 存放本身未被加工的模塊內容。
    this._rawModule = rawModule
    const rawState = rawModule.state
    // Store the origin module‘s state
    // 建立這個模塊的數據容器
    this.state = (typeof rawState === 'function' ? rawState() rawState) || {}
}
複製代碼

模塊的初始化主要是作了如下三件事情工具

  1. 建立_children屬性用於存放子模塊
  2. 建立_rawModule屬性存儲本身模塊的僞(未被加工)模塊時的內容
  3. 建立state屬性存儲本身模塊的數據內容 每一個模塊都有本身的state。

模塊的初始化並無作什麼事情,模塊提供的方法和屬性纔是它的核心, 模塊提供了一個namespaced的屬性,以及不少方法,我將模塊提供的方法分紅兩類。post

先說屬性

get namespaced () {
    // 獲取模塊的namespaced屬性 肯定這個模塊有沒有本身的命名空間
    return !!this._rawModule.namespaced
}
複製代碼

判斷是否有命名空間有什麼用?在之後設置getters、mutation、actions時有很大做用,之後再講。學習

再說方法

模塊提供的全部方法都是爲了給外部的調用,這些方法沒有一個是讓模塊在本身的內部使用的。因此我把方法劃分的緯度是,按照這個方法是用於構建模塊樹仍是用於抽取模塊中的內容ui

構建模塊樹的方法:this

1.addChild:給模塊添加子模塊。spa

addChild (key, module) {
    this._children[key] = module
}
複製代碼

這個方法實現上很簡單,它是在哪裏被調用的呢?你們能夠翻開上一章的moduleCollection的內容,在ModuleCollection中完成模塊之間的連接,就是使用這個方法給父模塊添加子模塊。 2. removeChild:移除子模塊 Vuex初始化的時候未使用,但能夠給你提供靈活的處理模塊的能力

removeChild (key) {
    delete this._children[key]
}
複製代碼
  1. getChild:獲取子模塊 獲取子模塊的意義是什麼?在之後配置模塊的名字時,須要獲取模塊的是否設置了命名空間,獲取命名空間的屬性模塊提供了,再提供一個獲取子模塊就都Ok了
getChild (key) {
    return this._children[key]
}
複製代碼
  1. updateChild:更新模塊的_ra wModule屬性(更新模塊的未加工前的模塊內容),Vuex中未使用
update (rawModule) {
    this._rawModule.namespaced = rawModule.namespaced
    if (rawModule.actions) {
      this._rawModule.actions = rawModule.actions
    }
    if (rawModule.mutations) {
      this._rawModule.mutations = rawModule.mutations
    }
    if (rawModule.getters) {
      this._rawModule.getters = rawModule.getters
    }
}
複製代碼

Vuex在連接與整合模塊的時候使用了其中兩個方法,addChild、getChild。類ModuleCollection在連接時須要找到模塊(getChild)而後給模塊添加子模塊(addChild)的功能,因此這兩個方法是在整合模塊時最重要的。

抽取模塊中的內容

上面的一組方法,是爲了更好的完成模塊的連接,給散落的單一模塊整理成一個模塊樹能夠提供便捷的封裝方法,下面要說的方法什麼叫作抽取模塊中的內容?將這些方法暴露給外面能夠方便的去獲取這個模塊內的一些內容來使用。

forEachValue是Vuex封裝的工具方法,用於遍歷對象的。

export function forEachValue (obj, fn) {
  Object.keys(obj).forEach(key => fn(obj[key], key))
}
複製代碼

這四個方法做用:

  1. forEachChild : 遍歷模塊的子模塊
  2. forEachGetter : 遍歷模塊中_rawModule.getters 這塊就應該知道 _rawModule的做用了,我把模塊未加工時會有getters屬性,存放這個模塊全部的getters方法(vuex的基本用法就很少講了),而後遍歷,
  3. forEachMutation : 和forEachGetter相似,只是換成了遍歷mutations
  4. forEachAction : 和forEachGetter相似,只是換成了遍歷actions

這四個方法就是遍歷這些內容,有意義嗎?

意義很大,目前_rawModule上這些getters、mutations、actions屬性並不會生效,只是單純的一個屬性,如何讓他們能夠成爲那種,被dispatch、commit使用的那種方法呢?先給你們一個小提示,mutations、actions都是要被註冊的,註冊以前總要獲取到這些內容,具體的實現方式後面的章節會詳細講述,

總結

加工後真正的module(咱們稱由Module這個類實例化出來爲真正的module)只是緩存了一些內容,而且給外界提供了一堆方便高效的方法。這些方便高效的方法爲以後的註冊action、mutation。整合state都起了很關鍵的做用。因此說module這個小單元爲下面的代碼提供了很大便利, 額外思考咱們對一段內容須要頻繁的處理而且處理方式大同小異的時候,是否是能夠像module同樣整理成一個對象,而後給外界提供一些方法。(有一種面向對象思想)

下一章講述action和mutation是如何調用的

我是一個應屆生,最近和朋友們維護了一個公衆號,內容是咱們在從應屆生過渡到開發這一路所踩過的坑,已經咱們一步步學習的記錄,若是感興趣的朋友能夠關注一下,一同加油~

我的公衆號:鹹魚正翻身
相關文章
相關標籤/搜索