解析 React Native 現行架構(Current Architecture)原理
長久以來,React Native 的效能問題一直為人詬病,為了解決這個問題,React Native 開發團隊針對舊有的架構進行了重構,並在 0.68 版本推出了新架構(New Architecture)。接下來,我會分享原來的架構是 Javascript 如何與 natvie 溝通,究竟面臨了什麼問題?讓 React Native 開發團隊決定重構。
要來了解現行架構是怎麼運作,先來認識幾個重要的概念:
Keywords
Javascript Engine
就是指執行 Javascript 程式碼的環境。
-
Hermes: 是基於 React Native 打造的 JS Engine,在 React Native 0.70 版時被設為預設的 JS Engine。
-
JavaScriptCore: Apple 開發的 JS Engine,較舊版本的 React Native 會使用這個引擎。
JSON 序列化(serizlized)
就是把資料轉換成 JSON 格式的過程,反之, JSON 反序列化就是把 JSON 格式轉成原始資料的過程。
Yoga engine
是一種跨平台佈局引擎(Layout engine),主要是用來計算使用者畫面中 UI 元素的位置,藉此生成每一個 React shadow node 的位置與大小,ex:把 Flexbox 佈局轉換成原生平台的佈局樣式。
React Native 利用三個主要執行緒(threads)進行運作
- UI Thread/ Native Thread: 是 UI Manager 負責處理用戶的介面操作 Andriod 跟 iOS 畫面的渲染邏輯,以及呼叫原生 api、運行原生模組。
- JavaScript Thread: 主要是 JS Engine 使用,負責運行 JS Bundle 中的 JavaScript 程式碼,處理邏輯。
- Shadow thread: 負責原生的佈局,提供給 yoga 引擎使用,其負責在渲染主機畫面(host screen)前計算佈局中元素的位子與大小。
現行架構(Current Architecture)
現行架構運作的流程
react 經過 Metro 打包編譯後產生 JS Bundle,JS Bundle 在 JavaScriptcore (JavaScript 引擎)的環境下執行,JavaScript 的程式碼與原生的程式碼透過 橋接(Bridge) 的方式溝通。
橋接(Bridge)是如何進行溝通呢? 原生模組(Native module) 透過 Bridge 封裝成 JavaScript 接口提供給 JavaScript 引擎呼叫 Native 的方法。
Native 與 JavaScript 之間溝通的方法是使用非同步的 JSON 序列化與反序列化方式去傳遞與轉換資料,也就是 JS thread 會傳送以 JSON 序列化的訊息並且以字串符發送到 Bridge,Bridge 會優化這個訊息並且傳遞到 UI Thread/ Native Thread,UI Thread/ Native Thread 收後解密這條訊息,然後根據這條訊息去執行原生的程式碼。
當應用程式啟動時,UI Manager 會下載所有的原生模組,React 會在 JavaScript Thread 執行產生 React Element Tree ,一旦渲染時就會透過 Bridge 發佈變更的指令到 Shadow Thread,創造 React Shadow Tree (似 React Virtual DOM 功能),顯示應用程序的 UI 的佈局和結構來比對 UI 需進行哪些更改,然後透過 yoga 引擎去計算 UI 元素在原生螢幕的位置和大小,一旦 Yoga 完成布局計算,React Native 的 UI Manager 就會將使用原生平台特定的 API 轉換成原生的 Host View Tree 並且通知 UI Thread 使用原生元素在用戶的螢幕上呈現變更後的 UI。