一年多前,Next.js 導入了 App Directory,並在今年六月正式進入穩定版。因此,我們在 Q3、Q4 開始計劃遷移到 App Router 的架構。這是 Crypto-Arsenal 前端系統的一次重要升級,包括樣式系統從 Styled-Component 轉移到 Tailwind CSS,採用 Storybook 作為前端測試工具,以及導入程式碼產生器和門檻值的規劃。在這篇文章中,我將紀錄遷移的理由、所採用的技術,以及未來延伸文章的預告。
Crypto-Arsenal 前端技術概觀
在 2021 年,Crypto-Arsenal 的前端曾經歷一次升級,以應對新版的網站設計等挑戰。該次升級主要調整程式碼架構,對於技術則只有必要的升級。當前我們採用的技術包括:
- Next.js Page Router
- Styled-Component (CSS-in-JS)
- Apollo Client (GraphQL)
- Storybook + Storyshots + Lost-Pixel
- Playwright
Next.js: Page Router → App Router
隨著 Next.js 將 App Router 設為建議,我認為未來的發展主力也將圍繞 App Router。遷移到 App Router 將有助於系統的健康,並提供更好的使用者體驗(如 Server Rendering 與 Code Spliting 等)。這次升級相對來說並不困難,但由於兩者的運作方式差異太大,我們需要將之視為新的 App 開發。由於也計劃進行大規模的程式碼調整,這對我們來說不是太大的問題。
Styled-Component → Tailwind CSS
在今年 Q1 左右,我們團隊開始檢討是否要使用 Tailwind CSS。主要原因在於 Styled-Component 的撰寫過度開放,導致開發規則不嚴謹,且對 Hydration 的支援不佳。雖然一開始對 Tailwind CSS 的作法有所疑慮,但我意識到樣式和邏輯混淆的問題實際上是一個通用的挑戰。最終判斷遷移到 Tailwind CSS 有助於程式碼的健康維護,並使 Snapshot Test 更容易理解。
Apollo Client
我們在今年初改為使用 GraphQL Code Generator。儘管沒有特別的遷移,但我們的程式碼包含許多過時的寫法,並未充分發揮 Apollo Client 的 Cache 能力。這次調整將透過更完整的 Type Policy 使 GraphQL 操作更加順暢。同時,我們將明確要求處理載入與錯誤狀態,以改進系統的穩定性。
Storybook + Storyshots + Lost-Pixel → Storybook + Test-Runner
Storybook 的遷移主要聚焦在測試方面。由於初版的產品定位是 MVP,缺乏自動化測試導致經常發生改動帶來的問題。原先使用的 Storyshots 與 Lost-Pixel 進行 Snapshot & Visual Testing 的嘗試未能全面實現。在配置新版本的 Storybook 時,了解到現在有 Test-Runner 可以做到 Snapshot 與 Visual Testing,同時讓設計師預覽預設的模擬操作,因此我們決定全面改用 Test-Runner。為了配合 Next.js 的 Server Component,我們使用了測試中的 Storybook v8。
Playwright
先前曾嘗試導入 E2E 測試,但由於程式碼的可測試性過低,最終無法運作。這次調整將同步加入 E2E 測試。
除此之外,我們還導入了程式碼產生器以及門檻值的概念。這是基於我閱讀了《Code That Fits in Your Head|軟體工程的啟發式方法》一書的建議。
程式碼產生:Hygen
前面提到,我們將明確要求撰寫各種測試,並為了降低人為錯誤,我們引入了程式碼產生器。在眾多的產生器中,我們選擇了 Hygen。它使用了 EJS 樣板引擎,撰寫樣板更加容易,同時提供了足夠的客製化空間,以避免未來需要更複雜產生規則時必須遷移到其他工具。
門檻值:Complexity 與 State 量
按照書中所說,我選擇循環複雜度(Cyclomatic Complexity)作為第一個門檻值,啟用了 ESlint 的檢查規則。我們以 25 為規則上限(合理狀況下可以忽略),35 為絕對上限(無論狀況),並且關閉 JSX Element 的計數。這兩個數字的選擇是基於 Microsoft 的標準值和 React 的撰寫習慣,未來不排除再次調整。另外,我選擇 State 數量為另一個門檻值,以 7 為規則上限,這則是基於人的記憶極限。
這次的架構調整主要圍繞著提升程式碼的可維護性。其一,遷移到新的架構,以確保未來的擴充能力。其二,導入更完整的測試來使我們對於程式碼改動更有信心,也避免其他團隊需要費時費力在尋找問題。其三,提升程式碼要求來避免程式碼品質衰退,同時透過程式碼產生器提高開發體驗。
我期望我們在 2024 Q1 完成遷移。在後續的文章中,我將撰寫各自的遷移心得,以及接下來遷移過程中發生的各種事情(希望不要是壞事)。
在〈Next.js 網站遷移到 App Router、Tailwind CSS、以及其他工具的紀錄〉中有 1 則留言