自定義 Babel 和 ESLint 外掛是如何提高生產率與使用者體驗的
一個正在探索森林的人(來源:unsplash.com/photos/ZDhL…)
自定義 Babel 和 ESLint 外掛是如何提高生產率與使用者體驗的
而且比你想象的容易很多...
我的前端大師課程 「程式變換(code transformation)與抽象語法樹(AST)」已經發布了? ?(進入網址檢視課程的簡介)!我覺得你們應該都有興趣瞭解為什麼要花上 3 小時 42 分鐘來學習編寫 Babel 和 ESLint 外掛
構建應用程式是件困難的事,並且難度會隨著團隊和程式碼庫的擴張而增大。幸運的是,我們有諸如 ESLint 和 Babel 這樣的工具來幫助我們處理這些逐漸成長的程式碼庫,防止 bug 的產生並遷移程式碼,從而讓我們可以把注意力集中在應用程式的特定領域上。
ESLint 和 Babel 都有活躍的外掛社群 (如今在 npm 上 「ESLint plugin」 可以搜尋出 857 個包,「Babel Plugin」 則可以搜尋出 1781 個包)。正確應用這些外掛可以提升你的開發體驗並提高程式碼庫的程式碼質量。
儘管 Babel 和 ESLint 都擁有很棒的社群,你往往會遇到其他人都沒遇到過的問題,因此你需要的特定用途的外掛也可能不存在。另外,在大型專案的程式碼重構過程時,一個自定義的 babel 外掛比查詢/替換正則要有效得多。
你可以編寫自定義 ESLint 和 Babel 外掛來滿足特定需求
應在什麼時候寫自定義的 ESLint 外掛
ESLint logo
你應該確保修復過的 bug 不再出現。與其通過 測試驅動開發(test driven development)達到這個目的,先問問自己:「這個 bug 是不是可以通過使用一個型別檢查系統(如 Flow)來避免?」 如果答案是否定的,再問自己「這個 bug 是不是可以通過使用 自定義 ESLint 外掛來避免?」 這兩個工具的好處是可以靜態分析你的程式碼。
通過 ESLint 你 不需要執行任何一部分程式碼即可斷定是否有問題。
除了上面所說的之外,一旦你新增了一個 ESLint 外掛,問題不僅在程式碼庫的特定位置得到了解決,該問題在任何一個位置都不會出現了。這是件大好事!(而且這是測試無法做到的)。
下面是我在 PayPal 的團隊使用的一些自定義規則,以防止我們釋出曾經出現過的 bug。
- 確保我們一直使用本地化庫而不是把內容寫在行內。
- 強制使用正確的 React 受控元件(controlled component)行為並確保每個
value
都有一個onChange
handler。 - 確保
<button>
標籤總是有type
屬性。 - 確保
<Link>
元件和<a>
標籤總是有合理的data
屬性以解析資料。 - 確保只在某個應用或共享資料夾內部匯入檔案(我們在一個倉庫(repo)裡有多個應用)。
我們還有更多的規則,但總的來說規則並不多。很讚的一點是,因為我們花了時間去學習並編寫自定義 ESLint 外掛, 這些 bug 都沒有再次出現。
注意:如果某個 bug 無法通過 Flow 或 ESLint 避免,那可能是業務邏輯出了什麼問題,你可以回到通過測試的方式來避免此類情況發生(學習如何測試 JavaScript 專案)。
應在什麼時候寫自定義的 Babel 外掛
Babel logo
如果你在思索:「那個 API 實在太無趣了」或是「我們不能那麼做,執行效率太低。」那你就應該考慮寫一個自定義的 babel 外掛了。
Babel 外掛 允許你調整程式碼。這一操作既可以在編譯時完成(以此來進行一些編譯時的優化),也可以是一個一次性的操作(稱為「codemod」,你可以把它想象成一種比正規表示式強得多的查詢替換功能)。
我很喜歡 Babel 的一個原因:
Babel 使我們可以同時提升使用者和開發者的體驗。
下面的例子說明了 babel 外掛是如何做到的這一點的。
- 在登陸介面就載入整個應用十分浪費資源,因此社群採取了「code-splitting」來避免這種情況。react-loadable則實現了 React 元件的延遲載入。如果你想實現更復雜的功能(如伺服器端支援或優化客戶端載入),就需要相對複雜的 API 了,然而,babel-plugin-import-inspector 已經自動為你處理好這一切了。
- Lodash 是一個使用很廣泛的 JavaScript 實用程式庫,但同時它也很大。一個小竅門是,如果你「cherry-pick」需要用到的方法(比如:
import get from 'lodash/get'
),只有你用到的那部分程式碼會被最終打包。babel-plugin-lodash 外掛會讓你正常使用整個庫(import _ from 'lodash'
)然後自動 cherry-pick 所需的方法。 - 我在構建 glamorous.rocks 網站(即將上線)時發現,無論使用者使用的哪種語言,所有本地化字串都會被載入!所以我寫了一個自定義的 babel 外掛基於
LOCALE
環境變數載入正確的本地化字串。這樣我們就可以為每種語言建立一個服務端渲染網站的靜態輸出,並開始在伺服器端為本地化字串使用 markdown 了(而我們之前會在 JavaScript 模組裡使用 markdown 的字串,完全是一團亂)。我們可以不再使用令人混亂的「高階元件(Higher Ordered Component)」來進行本地化,而可以在伺服器上匯入 markdown 檔案。最終網站變得更快且對開發者更友好了。
還有很多例子,不過希望這些已經足夠讓你認識到自定義 Babel 外掛所帶來的可能性了。
哦對了,你知道那些隨著框架和工具主要更新一起推出的 codemods 嗎?它們會像施魔法一樣 ✨ 把你的程式碼更新到最新的API(比如 React 的這個 codemod 或者 webpack 的這個 codemod)。你可以把那些工具寫成 babel 外掛然後通過 babel-codemod 執行(看看這個 babel-codemod 的演示)。(通過這篇演講深入瞭解 codemods,演講者 Chirstoph)。
我不管你的正規表示式用得有多好,自定義 babel 外掛可以讓你做得更好。
但是到底什麼是 AST?我可不是什麼火箭專家 ? !
astexplorer.net 上一個名為「你也許不需要 jQuery」的 babel 外掛演示。開啟連結:kcd.im/asteymnnj
Babel 和 ESLint 都以一個名為抽象語法樹(Abstract Syntax Tree,常縮寫為 AST)的結構為基礎執行。實際上這就是計算機如何讀取程式碼的。Babel 有一個 名為「babylon」的 JavaScript 語法分析器,可以把程式碼字串變成一個 AST(其實就是一個 JavaScript 物件),然後 Babel 把一些片段提供給 babel 外掛來讓你操作。如果是 Babel 則你可以做一些變形,如果是 ESLint 則你可以檢查你不希望出現的規則。
我沒有電腦科學的文憑。我一年前才開始學習 AST。
和 AST 打交道幫助我更深刻地理解了 JavaScript。
嘗試一下
我保證,這遠沒有你想象的困難?。你可以學好的。我會給你一步步地解釋。而且這門課還有很多非常好的練習幫助你進步。學習如何編寫自定義的 ESlint 和 Babel 外掛會對你的軟體開發之路有幫助,並且會讓你的應用變得更好 ?。
分享一下吧
自定義外掛是一個往往令人們生畏或疑惑的主題。如果這篇博文增進了你的理解,請分享給更多人,讓他們瞭解到學習編寫自定義 Babel 和 ESLint 外掛是多麼重要的技能。你可以通過 Medium 的 ? 分享,發推分享,或者轉推:
再見!@kentcdodds
P.S. 還有一些其他(免費)的資源可以幫助你學習 AST。
P.S.P.S 我覺得我應該提一下我最近寫的兩個 babel 外掛,它們讓我感到很興奮(I’m not alone either)我覺得你們應該看看這些外掛。這兩個外掛的最初版本我都只寫了半個小時:
- babel-plugin-preval: 在編譯時預分析程式碼
- babel-macros: 使 babel 外掛無需配置即可直接匯入
在課程裡,我會把所有編寫這樣的外掛需要的知識教給你。
掘金翻譯計劃 是一個翻譯優質網際網路技術文章的社群,文章來源為 掘金 上的英文分享文章。內容覆蓋 Android、iOS、React、前端、後端、產品、設計 等領域,想要檢視更多優質譯文請持續關注 掘金翻譯計劃、官方微博、知乎專欄。