一、背景git
今年年初,咱們在InfoQ發表了一篇題爲Flutter動態化在最右App中的實踐[1]的文章,主要講述了最右實踐Flutter動態化的方案,文章發佈至今愈來愈多的業內同窗聯繫到我,想了解更多關於最右Flutter動態化的細節,尤爲是iOS端的JS2Flutter框架,因而就有了展開系列文章詳解JS2Flutter框架的想法。github
這篇文章做爲JS2Flutter框架的開篇,後續將逐步介紹該框架的渲染機制、通訊機制以及依賴於Vsync機制的動畫和小遊戲的實現等核心技術點。一來分享實踐經驗,供感興趣的同窗參考;二來算做對本身在這個工做過程當中的總結。小程序
二、設計理念markdown
最右作Flutter動態化的初衷是要實現小程序和小遊戲的能力,知足增量獨立的業務場景,爲最右提供更多可能的技術選型。好比一些對交互體驗要求比較高的活動或者小遊戲就很適合這種方案,咱們不打算作最右主版本功能的遷移(成本太高也不必),而是穩健延伸App的能力,去承接一些非核心的業務場景。app
在作這件事情之初,咱們也肯定了這樣一些設計理念。框架
對Flutter開發者透明,無額外的學習成本,零成本享受Flutter生態資源。工具
Flutter側只負責UI渲染,控制邏輯在JS側。oop
渲染效率和靈活性之間的取捨更向效率傾斜。性能
三、JS2Flutter的誕生學習
3.1 方案選型
作Flutter動態化面臨的第一個問題就是技術方案選型,產物替換的方案是最簡單直接的,最右在Android端就是採用這種方案,可是因爲蘋果開發者協議的規定,不容許動態更新、運行可執行代碼,這條路在iOS端走不通。另外經過AOT搭載JIT這種方案,也面臨相似的風險。剩下一些可能的方案就是,靜態解析Dart語言生成UI描述或者相似RN運行時生成UI描述,前者最大的問題是工程量的龐大,對邏輯動態化的支持難度頗高,在最右這樣一個創業型的團隊,顯然沒有足夠的人力來完成這件事情,因此咱們選擇了相似RN的方案,只不過N再也不是Native了,而是Flutter。RN是經過JS控制Native渲染,咱們要實現的是經過JS控制Flutter渲染。
3.2 對開發者友好
類RN的方案,須要依賴JS來實現邏輯控制,怎樣才能不影響Flutter開發者的開發習慣,並能享用Flutter的生態資源,這是框架誕生前期思考的核心問題。
咱們借鑑學習了Flutter Web項目的實現思路,藉助dart2js這個強大的工具實現了Code In Dart,Compile It To JS。經過dart2js,咱們實現了對Flutter開發者透明,可讓開發者保持原有的Dart開發調試習慣,零成本支持Flutter Plugin,而且咱們開發了IDEA插件,可以便捷的編譯生成雙端動態化產物。
3.3 Hello World
咱們從最簡單的Hello World講起:
void main() => runApp(Text('Hello World'));
複製代碼
在這個過程當中,咱們須要完成哪些事情呢?
1.編譯成JS
2.動態下發
3.運行JS
4.把Text類信息和內容(Hello World)傳遞給Flutter
5.Flutter解析構造出真實的Text並渲染
前三步沒啥好說的,第四步其實就是UI描述的創建,想要讓Flutter渲染什麼類型的Widget,咱們須要經過JS告訴Flutter,因此這一步咱們要把所表達的信息數據化。好比這樣:
{ 'className': 'Text', 'data': 'Hello World', }
複製代碼
第五步咱們把拿到的數據解析出來,構造出真實的Text('Hello World')。固然第四五步之間還涉及到數據的傳遞,也就是須要創建JS到Flutter的通訊渠道,JS和Native之間經過JSCore創建通訊,Native和Flutter經過PlatformChannel創建通訊,這樣就能完成JS和Flutter之間的通訊。
3.4 框架誕生
想一想若是須要實現的Widget愈來愈多,不一樣場景的通訊也有不一樣的需求,咱們應該如何去維護這一套體系,JS2Flutter框架應運而生。從Hello World的實現過程咱們不難理解,框架必須包含這幾部分,一部分提供鏡像的Flutter Widget,負責構建Widget虛擬樹,並數據化傳遞給Flutter;一部分負責解析傳遞過來的數據,構建出真實的Widget樹;二者之間還有一部分去作通訊渠道的關聯,以及提供JS的運行環境,補全JS的一些能力等。
隨着框架的不斷演進和完善,造成了下圖呈現出來的結構。
3.5 框架詳解
如題,本文做爲JS2Flutter框架的開篇,起到提綱挈領的做用,後續會完成如下系列文章的講解:
1、最右JS2Flutter框架——渲染機制
2、最右JS2Flutter框架——通訊機制
3、最右JS2Flutter框架——動畫、小遊戲的實現
四、實踐經驗與成果
每一次的業務落地都是對框架的檢驗,從業務實踐中,逐步發現框架的問題,促進框架的完善。業務實踐不只能檢驗框架,還能促使框架以外的一些工具鏈誕生,逐漸完成流程自動化,提升研發效率等。隨着不斷的迭代打磨,JS2Flutter框架自誕生至今,已經在數十個活動類需求和小遊戲中獲得了應用,也經受住了大流量的考驗,在線上已穩定運行近一年。
下面是框架在2019年的最右五週年活動上落地的成果。
兩端的體驗都跟原生體驗很是接近,很是流暢。iOS端在有JS2Flutter框架的前提下,也並無明顯的性能折損。
五、業界發展近況
目前已知的Flutter動態化項目有騰訊開源的MXFlutter[2],以及美團的Flap[3],這兩個團隊在動態化方向上的投入都很積極。從MXFlutter的2020 RoadMap裏能夠看到他們在開發者友好度方面樹立了很明確的目標,開始支持業務由Dart開發,也有不少易用性方面的改進。Flap研發團隊放出來的信息相對於去年來講更加豐富,這確實是一個龐大的工程,要創建起這樣一套完整的體系絕非易事。
雖然都是去實現Flutter的動態化,但在實現方案上各個團隊的差別比較大。
六、結束語
最右的動態化框架一直在不斷演進,年初咱們是基於Flutter1.9.1+hotfix.6版本,現在已經升級到Flutter1.17.2,最右在Flutter動態化方向上的投入是很積極的,也積累了不少經驗。JS2Flutter框架是最右在探索Flutter動態化之路上的技術沉澱,後續將在系列文章中展開詳解,感興趣的同窗可持續關注。
七、參考文獻
[1]:Flutter動態化在最右App中的實踐 www.infoq.cn/article/MIa…
[2]:MXFlutter github.com/mxflutter/m…
[3]:美團外賣Flutter動態化實踐 mp.weixin.qq.com/s/wjEvtvexY…