開源中國專訪:Chameleon原理首發,其它跨多端統一框架都是假的?

開源中國專訪:Chameleon原理首發,其它跨多端統一框架都是假的?

原創: 嘉賓-張楠 前端

開源中國 vue

以往咱們說某一功能跨多端,每每是指在諸如 PC、移動等不一樣類型的設備之間都能實現;或者更加具體一點,指的是「跨平臺」,多是大到跨操做系統,好比 Windows、macOS、Linux、iOS 與 Android 等,多是小到跨某個具體技術的不一樣實現庫。git

可是今天咱們要介紹的是關於跨 MVVM 架構模式各類環境的場景。github

clipboard.png

Chameleon 是一套開源跨端解決方案,它的目標是讓 MVVM 跨端環境大一統,實現任意使用 MVVM 架構設計的終端,都能使用其進行開發並運行。 web

在這樣一個 MVVM 環境中,涉及到了 Weex、React-Native、WebView/瀏覽器與 Flutter 等各類跨端技術,還有它們實現的具體業務產品,好比微信小程序、快應用、支付寶小程序、百度智能小程序、今日頭條小程序與其它各種小程序。ajax

clipboard.png

也許你發現了,這裏提到了許多種「小程序」,雖然最先微信小程序的概念甚至早期版本出現的時候,有過很多不看好的聲音,可是隨着它不斷髮展,目前已經成爲了大衆生活不可或缺的應用形態。vuex

馬化騰透露過,截至 2018 年 11 月有 150 萬微信小程序開發者,小程序應用數量超過 100 萬,覆蓋 200 多個細分行業,日活用戶達到 2 億。這樣的成功經驗與幾乎觸及到生活方方面面的巨大流量入口,你們都想入場,因而能夠看到後來其它公司紛紛給出了相似的小程序方案。redux

另外一方面,除了小程序百花齊放,2018 年小米、華爲、OPPO 等 10 家安卓手機廠商還結成了快應用聯盟,而且前後發佈了一系列快應用。小程序

Chameleon 目標就是要跨這些端,而隨着各家不一樣實現愈來愈多,跨端場景也不斷變得更加複雜。咱們採訪了 Chameleon 創始人張楠,請他爲讀者具體分享了 Chameleon 在這個過程當中的成長。後端

項目地址:https://github.com/didi/chame...

本文是 Chameleon 首次對外公開實現原理!

乾貨超多,包括:

  • 終端開發將來的開發模式
  • Chameleon 跨端實現原理
  • 當前各類跨端方案原理對比(各類小程序、快應用等)
  • 與 Taro 的對比
  • 演進過程當中遇到的困難與思考

當初爲何去研發 Chameleon?

關於這個問題能夠從行業背景講起。

中國互聯網絡信息中心(CNNIC)發佈的《中國互聯網絡發展情況統計報告》顯示,截至 2018 年 6 月,我國網民規模達 8.02 億人,微信月活 10 億 、支付寶月活 4 億、百度月活 3.3 億;另外一方面,2018 Q3 中國 Android 手機佔智能手機總體的比例超過 80%,月活約 6 億。

BAT 與 Android 成爲了中國互聯網真正的用戶入口。但凡流量高的入口級別 APP 都但願作平臺,成爲一個生態平臺和互聯網流量入口,大量第三方應用的接入,從業務層讓公司 APP 關聯上更多企業的利益,而且擁有更強的生命力;從技術層面能夠利用「本地能力接口層」收集大量用戶數據,從消費互聯網到產業互聯網須要大量各行各業基礎用戶數據線索進行驅動和決策。

在這麼一種背景下,再結合計算機技術的發展歷史,咱們知道每一種新技術的出現都會經歷「各自爲政」的階段,小程序技術也不例外,因此咱們看到了其它各類小程序平臺出現。

微信小程序做爲獨創者,雖然其它小程序都有在技術實現原理、接口設計上刻意模仿,可是做爲一線開發者在不一樣平臺發佈小程序,每每仍是須要重複開發、測試,從前 1 單位的工做量變成了 N 單位的工做量。而這還沒算上快應用等其它入口。

這種狀況下,滴滴的研發工程師是其中最顯著的「受害者」之一,滴滴出行在微信錢包、支付寶、Android 快應用都有相關入口,並且用戶流量佔比不低。

研發同窗在端內既追求 H5 的靈活性,也要追求性能趨近於原生。面對入口擴張,主端、獨立端、微信小程序、支付寶小程序、百度小程序、安卓廠商聯盟快應用,單一功能在各平臺都要重複實現,開發和維護成本成倍增長。

迫切須要一個只維護一套代碼就能夠構建多入口的解決方案,因而咱們着手去打造了 Chameleon(CML,卡梅龍)這麼一個項目,真正專一於讓一套代碼運行多端。

Chameleon 核心是運用了 MVVM 架構,爲何它能夠實現跨多端?

MVVM 也就是 Model View ViewModel,它本質上是 MVC( Model View Controller)的進化版本,將 View 的狀態和行爲抽象化,使得視圖 UI 和業務邏輯分開。

它是一種讓數據驅動反射視圖的模式,發展到如今可能會偏離它的初衷了,更像是一個視圖數據間的「通訊協議」,讓終端開發變得更加單純,這是一種趨勢,面向將來框架都採用這種模式。

clipboard.png

Facebook 在 2013 年開源 React,React 這個項目自己是一個 Web UI 引擎,隨着不斷髮展,它衍生出 React Native 項目,用來編寫原生移動應用。正是它給跨端方向帶來了 MVVM 模式。

Vue.js 於 2014 年左右發佈,逆流而上佔據了大量用戶羣體,2016 阿里巴巴也基於它發佈了 Weex 項目,使得能夠用 Vue 編寫 Native App。

Google 在 2018 年底正式發佈了面向將來的跨 Android、iOS 端的 Flutter 1.0.0。

原理

咱們知道終端開發離不開三大要素——界面表現(結構、外觀)層、邏輯處理層與系統接口層(網絡、存儲與媒體等)。

clipboard.png

開發者編寫代碼時在初始化階段(生命週期)調用「界面表現層」界面模型的接口繪製界面,當用戶觸摸界面時,「界面表現層」將事件發送給用戶「邏輯處理層」,後者通過條件判斷再處理並反饋到用戶界面,處理過程可能須要調用「系統接口層」,反饋過程須要調用「界面表現層」的接口。

常規的終端開發架構模式下,不管是 Web 端、Android 端仍是 iOS 端的項目開發,都強依賴各端的環境接口,特別是依賴界面相關模型設計。

iOS 系統下繪製界面基於 Objective-C 語言環境下的 UIKit 框架;Android 系統下用戶繪製界面基於 Java 語言環境,由 LayoutInflater 處理 XML 結構層次樹;Web 端使用 DOM 模型和 CSS 來描述繪製界面。  

MVVM 中的關鍵是它經過 ViewModel 這一層將界面和邏輯層完全隔離開來,負責關聯界面表現和邏輯處理層的響應事件(update/notify)關係,這一「隔離層」上下通訊足夠規範、足夠純淨單一。  

Model 進行邏輯處理是純業務響應邏輯,任何一種語言均可以實現,你能夠用 Android 的 Java,也能夠用 iOS 的 Objective-C,你心情好用「世界第一語言 PHP」也能實現。

之因此廣泛選擇 JavaScript,很大程度是由於在這個領域內它的優勢顯著,如學習成本低、天生具有跨端屬性、虛擬機(V八、JavaScriptCore)和各方向組件建設較好、生態活躍。

而系統接口層則更簡單了,只需窮舉統一基礎接口+可擴展接口能力便可。

各類 MVVM 方案

具體來看看各類 MVVM 方案都是怎麼樣的。

React Native、Weex 與快應用的 MVVM

clipboard.png

開發者編寫的代碼在虛擬機(V八、JavaScriptCore)裏面運行,虛擬機容器裏面包含擴展的系統基礎接口。運行時,將描述界面的數據(主要是 CSS+DSL 所描述內容)經過通訊層傳遞給 Android、iOS 端的渲染引擎,用戶觸摸界面時,經過通訊層傳遞給虛擬機裏面的業務處理代碼,業務處理代碼可能調用網絡、儲存與媒體等接口,最後再次反饋到界面。

Flutter 的 MVVM

Flutter 和 RN 的最大區別在於將「JavascriptCore/V8+JS」替換成「C++ 實現的 engine+Dart 實現的 Framework+靜態類型 Dart+編譯成機器碼」。

Flutter 的方案以下圖所示:

clipboard.png

Service 其實就是本地能力接口層,Widget 樹是視圖層模型。

clipboard.png

Flutter 和 RN 的使用面設計上相似,Flutter 文檔中提到「In Flutter, almost everything is a widget.」,widget 的調用從 RN 的 JSX 變成 Flutter 的 widget 調用,UI 的外觀描述從 RN 的 CSS(文本樣式、佈局模型、盒模型)到定製化 Flutter Widget(textStyle 、Layout Widget、Widget)。

clipboard.png

本質上 Flutter 也是 MVVM 架構,邏輯層經過 setState 通知視圖層更新,必定程度上這也是爲何 Flutter 敢說能轉成 Web 框架的緣由,核心仍是基於這類數據驅動視圖架構模式,業務代碼不會深度依賴任何一端特有的「視圖模型」。

各種小程序的 MVVM

小程序本質上和 Weex、React Native 的設計思路基本同樣,最大區別在於前者仍是用瀏覽器 WebView 作渲染引擎,然後者是單獨實現了渲染引擎(因此大量的 CSS 佈局模型不支持)。

clipboard.png

具體到 Chameleon 上是怎麼實現的?

首先任何一份應用層的高級語言代碼塊分紅幾層:語言層(Language)、框架層(Framewrok)與庫層(Library):

  • Language —— 通俗來講,實現程序所需的基本邏輯命令:邏輯判斷(if)、循環(for)與函數調用(foo())等。
  • Framewrok —— 通俗來講,完成一個 App 應用交互任務所需規範,例如生命週期(onLoad、onShow)、模塊化與數據管理等。
  • Library —— 能夠理解就是「方法封裝集合」。好比 Web 前端中 Vue 更適合叫框架,而 jQuery 更適合叫庫;Android 系統下 activity manager + window Manager  View System 等的集合叫框架,而 SQLite 、libc 更適合叫庫。

對應到 Chameleon 就是這樣:

clipboard.png

具體到實現原理全景架構圖以下:

clipboard.png

你能夠理解 Chameleon 爲了實現「讓 MVVM 跨端環境大統一」的目標作了如下工做:

  • 定義了標準的 Language(CML DSL)、Framework 與 Library(內置組件和 API)協議層。
  • 在線下編譯時將 DSL 轉譯成各端 DSL,只編譯 Language 層面足夠基礎且穩定的代碼。
  • 在各個端運行時分別實現了 Framework 統一,在各個端儘可能使用原有框架,方便利用其生態,這樣不少組件能夠直接用起來。
  • 在各個端運行時分別實現了 Library(內置組件和 API)。
  • 爲用戶提供多態協議,方便擴展以上幾方面的內容,觸達底層端特殊屬性,同時提高可維護性。

clipboard.png

實現思路很簡單,全部設計爲了 MVVM 標準化,不作多餘設計,因此宏觀的角度就像 Node.js(libuv)同時運行在 Windows 和 macOS 系統,都提供了一個跨平臺抽象層。

從 MVVM 角度來看的話:

  • View(展示層)
  • 第三方 Render Engine:各種框架已有框架,瀏覽器的 Vue、Webview 裏的小程序引擎、Android、iOS 裏面的 React Native/Weex 引擎、甚至 Flutter 裏面的 Dart Framework。
  • Chameleon 內置組件庫:多態協議定義統一組件 view、input、text、block 與 cell 等,它是界面組層的原始基類,衍生出多複雜界面功能。
  • ViewModel(關聯層)Chameleon 語法轉譯
  • 組件調用
  • 循環
  • 條件判斷
  • 事件回調關聯
  • 父子關係
  • ……
  • Model(邏輯響應層)
  • JavaScript 代碼
  • CML Runtime 框架
  • Chameleon API:多態協議定義統一接口,cml.request、cml.store 等

Chameleon 的跨多端方案給開發者的開發帶來了極大的便利,具體表現是怎麼樣的?

一句話:基於 Chameleon 開發,效率會愈來愈高

各個端的涌現,讓本來是 1 的工做量由於多端存在而變成 N 倍,使用 Chameleon,工做量會變回 1.2。這多出來的 0.2 工做量是要處理各端的差別化功能,好比如下場景:

  • 某業務線遷入 Chameleon 時,發現沒有「passport登陸組件」,在各種小程序裏面能免密登陸了,在 Web、Native 端是彈出登陸框登陸,不一樣業務用戶交互形態不同因此 Chameleon 沒有提供組件;開發者須要基於多態協議擴展單獨一個登陸組件<passport/>,不管如何最後返回一個登陸後的回調 token 便可,外部無需組件關內心面如何操做。
  • 用戶須要分享功能,發現沒有「share組件」,在微信 Web 端能夠引導右上角分享,在小程序直接分享,不一樣業務用戶交互形態不同,用戶須要基於多態協議擴展單獨一個登陸組件<share/>。

這種各端差別較大的例子,隨着業務的積累,能夠變成了一個個業務組件單獨維護,後面也不須要重複開發了,且反推產品體驗一致化,組件三層結構「CML框架內置組件->CML擴展組件->業務開發者本身擴展的多態組件」達成 100% 統一。

隨着組件積累業務開發工做量越來少,工程師能夠專一作更加有意義的事情,這就是 Chameleon 存在的目的。

基於統一的跨端抽象,用戶在 Chameleon 項目持續維護過程當中,Chameleon 發佈新增一個端以後,你的業務代碼基本不用改動便可無縫發佈成新端。

好比這個 cml-yanxuan 項目開發時支持 3 個端,後面新增了百度、支付寶小程序端,原有代碼直接能跑起來運行 5 個端,一端所見即多端所見。

開發時只能跑 3 個端

clipboard.png

原有代碼無縫支持 5 個端

clipboard.png

另外特別強調的是,對於大公司團隊,若是有很強的技術能力,但願開發的代碼掌控在本身手裏,對輸出結果有更好控制能力。其實 Chameleon 內置組件和內置 API 是能夠替換的,那麼全部組件都是業務方本身開發了,哪天不想用了直接導出原生組件便可離開 Chameleon,以下圖:

clipboard.png

目前跨多端統一的方案中,Taro 是比較亮眼的,可否具體對比一下 Chameleon 與 Taro。

咱們以爲 Chameleon 與其它解決方案的最大區別在於其它框架都是小程序加強,即用 Vue 或者 React 寫小程序,這些框架官方給的已接入例子也都是跑微信小程序。

它們更加相似 Chameleon 的前身 MPV(Mini Program View),即考慮如何加強小程序開發。2017 年微信小程序發佈時,滴滴做爲白名單用戶首先開始嘗試接入,開始面對重複開發的難題。

這時候咱們專門成立了一個小項目組,完成一個名爲 MPV 的項目,一期目標是「不影響用戶發揮,不依賴框架方的原則性實現一套代碼運行 Web 和微信小程序」。

看着很美好,用這樣的方案實現 Web 端和小程序端,也確實完成了超過 90% 代碼重用,整體上開發效率和測試效率都有了必定提高,可是卻不是真正意義上的跨多端統一。

單獨說到 Chameleon 與 Taro 的區別,整體上看,能夠歸爲這樣一個表:

clipboard.png

表中每一項都是在作跨端方案時須要考慮到的。咱們說除了 Chameleon,其它方案都只是在對小程序進行加強,或者說是模仿微信小程序的 API 和組件的接口設計。

Taro 是經過將 JSX 轉成小程序模板,在其它端模擬微信小程序的接口和組件,讓其它端更像微信小程序,業務開發時不一致的地方須要環境變量判斷差別分別調用,會形成端差別邏輯和產品邏輯混合在一塊兒。

此外,它要跟隨小程序更新,業務方會有雙重依賴;其它端的和小程序不能保持一致,用戶要各類差別化兼容,不利於維護。

那 Chameleon 呢?Chameleon 把這些問題都考慮到了,因此在早期僞跨端 MiniProgram View 成型以後不斷演進的過程當中,把它發展成爲一個真正的跨多端方案。

前邊的表格顯示了,Chameleon 既考慮統一性,又考慮差別性,且差別性不會影響可維護性;當各端差別確實太大,那就不要用一套代碼實現多個端同一頁面,而是統一公用組件。

這還只是拿 Chameleon 與 Taro 的重合點進行了對比,可是別忘了 Chameleon 不只僅是前端框架,它:

  • 還有統一的 Chameleon Native  SDK,Chameleon 不只僅但願統一各種小程序,還要覆蓋自家 APP,會持續經過 Native SDK 擴展 API 和組件,指望有與小程序同樣的本地能力。理想狀況下,一套代碼就能在各種小程序、自家 APP 裏面無縫平滑運行。
  • 還有待開源的後臺管理系統。
  • 還有待開源的 XEdtior 非研發用編輯器,能夠直接編輯跨端頁面、直接發佈。

另外,將來還將帶來如下能力:

  • 後端統一接口(消息推送、分享與支付等)
  • 基於統一的 MVVM 標準,更有基於 Flutter 的原生 APP

當前的各種小程序和 Native 跨端框架,相似當年多個瀏覽器時,Safari、Chrome、Firefox、IE 6/7/8/九、Android 瀏覽器等盛行的時代。以這個來類比,那麼 Chameleon 的接口組件設計上更像一個 jQuery。

網絡請求有的是 XHRHttprequest 有的是 ActiveXObject,jQuery 考慮的是用戶須要什麼,須要一個網路請求接口,支持 get、post 等,因此 jQuery 寫一個既非 ActiveXObject 又非 XHRHttprequest 的名爲 $.ajax 接口,提供一個封裝網絡接口,你不用關心內部在不一樣端怎麼調用的,jQuery 內部會幫你兼容。

Chameleon 也是同樣的思路,全部的接口設計都是真正能兼容跨全部的端,沒有差別性,並且只保留當前所在端的接口調用代碼:IE 裏面只保留 ActiveXObject,Chrome 只保留 XHRHttprequest。

Chameleon 的接口設計上比 jQuery 更強的地方在於,使用標準的多態協議,保障可維護性,性能上只保留當前端代碼,且將多態協議暴露出來,讓用戶也能擴展本身想要的 API(類比 $.xxx)。

固然時代已經變了,監聽視圖不在是 $('#xxx').click(fn),而是 MVVM 數據驅動視圖方式了,因此提供了 Chameleon 雙向綁定這樣的 VM 層。

前邊講到了 Chameleon 的前身 MPV,那具體分享一下 Chameleon 的整個演進過程吧。

出生期:選擇轉譯仍是模擬小程序環境?

前面講到,2017 年的時候,咱們完成一個名爲 MPV 的項目,一期目標是不影響用戶發揮,不依賴框架方的原則性實現一套代碼運行 Web 和微信小程序。

當時缺少小程序資料是遇到的最大問題(就更別提今天講到的業內這麼多解決方案了),當時惟一一個能夠參考的開源項目是 WEPT,WEPT 是一個微信小程序實時開發環境,它的目標是爲小程序開發提供高效、穩定、友好、無限制的運行環境。它的設計思路是在 Web 端模仿小程序環境執行。

因而咱們在開發 MPV 時考慮了兩種實現策略:

一、在 Web 端像 WEPT 同樣 mock 小程序環境;就像微信開發者工具裏面也模擬了小程序執行環境,WAServie、WAWebview 提供的兩套環境源碼作底層,在頁面中開啓三個獨立運行環境運行並用 iframe 通信模擬微信小程序的 3 個 Webview 之間的聯通關係。

二、逐個轉譯代碼支持小程序,缺點是可能會有 edge case 須要處理以及潛在的 bug 會比較多。

最終在看完 WEPT 源碼和微信開發者工具的狀況下,咱們明確放棄了第 1 條實現策略,選擇了逐個轉譯代碼支持小程序的路線,主要緣由是於 Web 端兼容微信全部的功能,尺寸過於龐大。

通過三個月緊鑼密鼓的開發終於實現了初版本 MPV:  

clipboard.png

通過實現幾個 demo 以後,開始執行遷移計劃:

clipboard.png
 

MPV 在 Webapp 上實踐最終實現效果以下:

clipboard.png

最終實現效果挺美好,也確實完成了超過 90% 的代碼重用,整體上開發效率和測試效率都有了明顯提高。

可是在後續實踐過程當中,發現存在大量的問題,而且項目越大問題越凸顯出來,總結以下:

  • 可維護性問題,沒有隔離公用代碼和各端差別代碼。項目中不止有業務邏輯,還混雜着 Web 端和小程序端產品功能差別化邏輯。好比前邊舉過的例子,分享功能 Web 端沒法實現(引導分享),小程序能夠實現,意味着各類環境判斷各類差別化邏輯,牽一髮動全身,還要來回測試。
  • 方向選擇錯誤,MPV 使用了小程序語法標準(小程序的生命週期、API 接口等),致使用戶使用上沒法清晰理解。
  • 不能直接使用各端已有生態組件,即缺少標準規範接入某個端已有開源組件。好比 Web 端 pick.js 組件缺少快速接入規範,用戶要麼從新開發,或者在模板和 js 代碼中使用環境判斷的方式針對引入。最終致使同一功能不一樣端的調用方式、輸入與輸出不一致。
  • 業務項目依賴 MPV 框架。框架依賴微信小程序接口(模板、生命週期與接口),擴展了統一接口。例如微信小程序更新了 wx.request 時,業務項目方沒法馬上使用,須要等框架更新。
  • 文件夾結構混亂,混雜着多個端代碼文件,且識別成本高。
  • 不支持 vuex、redux 等高效數據管理方式
  • 尺寸單位不統一,px 和 rpx 不一致
  • 周邊小型差別點太多:
  • 協議不一致,例如 Web 端能夠用 //:www.didiglobal.com/passenger/create ,小程序只能用 https://:www.didiglobal.com/passenger/create
  • 打開一個新頁面時連接不統一,例如打開發單頁時,Web 端是 //:www.didiglobal.com/passenger/create,小程序是 /page/create
  • 頁面之間跳轉時,傳參不統一
  • debug 成本高,修改完代碼以後兩端須要測試
  • 兩端界面效果不一致,基礎內置組件統一性建設不足
  • 工程化建設落後,例如不支持 liveroload、數據 mock、資源定位、proxy、多端統一預覽
  • 接口設計不完整,生命週期、組件分層、本地 API 設計等
  • 模板 DSL 語法不規範

成長期:從僞統一到大一統

在 MPV 的實踐積累下,有了必定的底氣和把握,後續的規劃更加明確。2018 年 4 月咱們把跨端項目規模進一步擴大,想要作一個真正跨 N 端的解決方案,目標是提供標準的 MVVM 架構開發模式統一各種終端。這就是 Chameleon 的出現契機。

Chameleon 真正想要一套代碼運行多端,總結下來要解決幾大問題:

  • 要全面完成端開發的全部細節的統一性,特別是界面統一性有大量細節要作
  • 要在完成上一條的前提下考慮差別化定製空間
  • 持續可維護

clipboard.png

目標理想業務形態是這樣的:

clipboard.png

圖中上半部分是傳統開發方式,下半部分 Chameleon 的模式抽象出了 UI 渲染層和本地接口能力層,業務代碼一部分簡單頁面由 XEditor(h5Editor 的前身)編輯工具產出,另外一部分工程師使用 Chameleon 開發,不止解決跨端問題,還彌補改進了工程開發過程當中的效率、質量、性能與穩定性問題,讓工程師專一有意義的業務,成長更快。

首個 Native 渲染引擎選擇——小程序架構、RN/Weex 架構

從 MPV 到 Chameleon,外界看來最明顯的變化是從跨 2 端(Web、小程序)升級到跨多端(Web、小程序、Android、iOS),最開始糾結於首個端上版本的渲染引擎使用小程序架構仍是 RN/Weex 架構。

RN/Weex 網上有大量資料可查,可是小程序方面則否則。千辛萬苦搜索以後,根據一位知道內情的朋友的描述分享,纔有了必定的瞭解。

 
clipboard.png

這裏分享幾個印象深入的要點:

  • 小程序展示層使用 Webview,裏面內置了一套 JS 框架用來和 Native 通訊,真正業務代碼執行在單獨 JS 虛擬機容器實例中
  • JS 虛擬機容器使用狀況,iOS 系統是 JavaScriptCore,Android 系統使用 QQ 瀏覽器的 X5 內核
  • 小程序的各個 TAG 組件使用的數據驅動用的是 Web Components
  • 顯而易見,部分性能要求較高的使用原生控件(視頻、鍵盤等等)插入到 Webview 裏面。
  • 原生控件的具體位置 Native 怎麼獲取?答案是由嵌入到 Webview 的一套小程序框架通知給原生層
  • 原生控件怎麼保證在內部可滾動的元素(Scroll-view)裏面正常滾動?答案是 CSS 設置 -webkit-over-scroll:touch 時,iOS 的實現是原生的 UIScrollView,Native 能夠經過一些黑科技找到視圖層級中的 UIScrollView,而後對原生控件進行插入和處理;而 Android 直接繪製沒辦法作到這點。如今(截至 4 月)僅僅是直接覆蓋到 Webview 最外層的 scrollview 上,由內置到 Webview 的一套 JS 框架控制原生控件位置

最終多方面分析以下:

clipboard.png

雖然小程序方案看起來很簡單,但其實不少細節點須要大量打磨,從確認方案到真正能夠跑起來能夠線上發佈,僅僅花費在終端上的研發人力爲 20P*6 個月,微信小程序團隊的目標和咱們跨端目標不同,他們投入這麼多成本是值得的,咱們爲了跨端不必投入這麼高成本。

因此咱們選擇放棄小程序渲染方案,而使用已開源的 RN/Weex 方案

第一個版本最終使用 Weex,包括團隊同窗去看了 Weex 源碼實現。

在總體設計上僅僅使用 Weex 渲染功能,外層包裝接口,保障後續能有更高擴展性。

Chameleon Native SDK

針對 Native SDK 咱們主要從原生能力擴展、性能與穩定等三個方面作了工做。 

clipboard.png

  • 原生能力擴展:不管是 Webview 仍是 React Native、Weex 甚至 Flutter 都只提供渲染能力(以及一些最基礎本地接口),更多完成業務功能所需本地環境的能力(例如分享到微信)須要 Android 和 iOS 的 Native 往容器去擴展。本地能力包含 2 種,涉及 UI 界面的統一叫組件(UI 組件如登陸、支付),涉及到純能力調用的統一叫 API(網絡、存儲等)
  • 性能:界面展示和交互耗時關鍵取決於 2 塊,資源加載耗時(非打包到安裝包部分代碼)、執行耗時
  • 穩定:主要關注灰度發佈(風險可控)和線上止損,主要工做是按用戶灰度發佈、能夠快速降級到 H5

如下是性能方向中的首屏加載時間的優化數據,原有 H5 使用 SSR(Server Side Render)已經算是最快的 Web 首屏技術方案了(不考慮優化後端多模塊耗時的 BIGPIPE),它保持在 1.5 秒如下,在優化後降到 0.5 秒左右。  

clipboard.png

 

性能優化中咱們有一個關於執行速度的 TODO 計劃。一樣是跨端,Flutter 之因此比 Weex 和 RN 執行速度快,主要緣由是前者是編譯型,客戶端機器運行前已是 CPU 可識別的機器碼;後者是解釋型,到客戶端運行前是字符串,邊編譯邊執行,雖然作了 JIT 儘可能優化,差距仍是較大。其實在這中間還有一個抹平了不一樣 CPU 架構下機器碼差別的中間碼;固然前提是開發語言改爲靜態類型,這裏不做展開。

本來分 5 次開發的 Web 端、支付寶小程序、快應用、微信小程序、Native 端變成了 1.2 次左右開發了。最重要的是隨着業務級別各端差別化的多態組件和跨端組件積累,後續 1.2 工做量也會變成 0.8,0.4 的優化主要來自兩個方面:

  • 0.2 是普通跨端組件的積累,複用度變高
  • 0.2 是各種業務級別的差別化多態組件,例如登陸功能,在 Web端、Native 端和小程序端實現和交互是不一致的,這時候業務形態不同,設計的 <passport> 組件也不同,只能各業務線去封裝。

介紹一下接下來的 roadmap。

咱們的最終目標是提供標準的 MVVM 架構開發模式統一各種終端。

clipboard.png

接下來的具體 roadmap 以下表所示:

clipboard.png

歡迎有共同願景的同窗加入咱們一塊兒共建,往倉庫貢獻本身的代碼。

項目地址:https://github.com/didi/chame...

QQ 羣:

clipboard.png

公衆號:

clipboard.png

採訪嘉賓介紹

張楠,Chameleon 創始人,技術團隊負責人,前百度資深工程師,終身學習者。

相關文章
相關標籤/搜索