webpack雖然使用簡單,可是它對於使用者就是一個黑盒。webpack
魯迅說:若是你對一個事物原理不瞭解,那麼你不可能熟練駕馭它。web
若是有不熟悉webpack基本使用的小夥伴們,能夠查看我以前的分享,能夠狠狠的點擊這裏:https://segmentfault.com/a/11...segmentfault
咱們能夠把webpack理解爲一條生產線,須要通過一系列處理流程後才能將源文件轉換成輸出結果。這條生產線上的每一個處理流程的職責都是單一的,多個流程之間會存在依賴關係,只有完成當前處理後才能交給下一個流程去處理。promise
咱們的插件就像一個插入到生產線中的一個功能,在特定的時機對生產線上的資源會作處理。webpack它是經過 Tapable來組織這條複雜的生產線的。數據結構
webpack在運行的過程當中會廣播事件,插件只須要關心監聽它的事件,就能加入到這條生產線中。而後會執行相關的操做。webpack的事件流機制它能保證了插件的有序性,使整個系統的擴展性好。事件流機制使用了觀察者模式來實現的。app
總的來講,tapable暴露了3種hooks:異步
事件名稱 | 說明 |
---|---|
entryOption | 初始化options |
run | 開始編譯 |
make | 從entry開始,遞歸分析依賴,並對依賴進行build |
build-module | 使用loader加載文件,並build模塊 |
normal-module-loader | 對loader的文件進行acorn編譯,生成抽象語法樹AST |
program | 開始對AST進行遍歷,當遇到require時觸發call require事件 |
seal | 全部依賴build完成,開始對chunk進行優化(抽取公共模塊、加hash等) |
optimize-chunk-assets | 壓縮代碼 |
emit | 把各個chunk輸出到結果文件 |
compiler對象 是Compiler類的實例對象, 而Compiler類繼承自Tapable,webpack在啓動時,會實例化一次compiler,後續每次文件的改動,都會建立一個compilation對象。優化
Compiler 負責文件監聽和啓動編譯。Compiler 實例中包含了完整的 Webpack 配置,全局只有一個 Compiler 實例ui
compiler對象,大體數據結構以下:spa
咱們在開發自定義插件時,webpack會調用插件類的apply方法,傳入compiler,咱們就能夠在tapable廣播事件流時,自定義作一些事件啦~
掌握webpack的工做原理,對咱們後續開發本身的loader, plugin有極大的好處。後面我將分享,如何開發本身的plugin。碼字不易,多多關注~😙