背景
app內(nèi)已完成rn模塊的集成
jsbundle以靜態(tài)文件的方式隨app發(fā)版载萌,缺少熱更新能力
熱更新能提高發(fā)版的效率
需要建設(shè)熱更新包管理平臺
熱更新的概念
不用重新發(fā)布app版本,即不用更新app的安裝包巡扇,在用戶無感知的情況下扭仁,就可以對應(yīng)用實(shí)現(xiàn)版本迭代、bug修復(fù)的技術(shù)解決方案稱為熱更新
對比常規(guī)開發(fā)流程而言霎迫,熱更新的開發(fā)流程更加靈活方便斋枢,優(yōu)勢很多:
無需提交商店審核,實(shí)時(shí)發(fā)版
用戶無感知知给,無需下載新應(yīng)用瓤帚,代價(jià)小
版本覆蓋率高,新功能可快速觸達(dá)用戶涩赢,避免依賴app的版本升級
實(shí)現(xiàn)方式
react-native使用腳本語言js開發(fā)戈次,具有“即讀即運(yùn)行”的特性,在“讀”之前將之替換成新版本的腳本筒扒,運(yùn)行時(shí)執(zhí)行的便是新的邏輯了怯邪。js語言可以通過jsbundle的方式下載到app內(nèi),然后通過js引擎執(zhí)行花墩。繼而可以實(shí)現(xiàn)最新的代碼悬秉,不通過應(yīng)用商店,直接下發(fā)到app內(nèi)冰蘑。
存在的問題
需要后臺支持和泌,不然無法實(shí)現(xiàn)包的分發(fā)
線上客戶端會存在多個版本,根據(jù)不同版本的具體差異的不同祠肥,可能需要根據(jù)不同的客戶端版本武氓,下發(fā)不同的熱更新內(nèi)容
需要管理好app的版本和jsbundle包的版本,否則會出現(xiàn)線上問題
解決方案
jsBundle包需要一個后臺服務(wù)來上傳、管理和分發(fā)县恕,需要區(qū)分不同的環(huán)境:feature东羹、uat、production等
需要封裝客戶端sdk忠烛,封裝向平臺請求jsbundle包属提、傳輸解密、版本管理等功能
系統(tǒng)架構(gòu)
包管理平臺
提供應(yīng)用管理美尸、應(yīng)用版本管理垒拢、js包管理、js包上傳和分發(fā)火惊、異常時(shí)的回滾、傳輸過程中的加密奔垦、條件下發(fā)等功能
客戶端SDK
提供了向后端請求js包屹耐,js版本管理、傳輸后的解密等功能
主要流程
熱更新流程如下
前置工作:
-
在熱更新平臺創(chuàng)建App應(yīng)用: 即需要接入熱更新的app。
設(shè)置應(yīng)用名稱、應(yīng)用版本撕捍、管理員等信息
后續(xù)需要獲取到當(dāng)前app應(yīng)用的所有上線版本(或許需要打通app的Jenkins平臺自動維護(hù)版本甫菠,或者手動維護(hù))。
-
創(chuàng)建js包應(yīng)用:
選擇需要投放的app寿桨,可以多選。
設(shè)置git倉庫
設(shè)置打包腳本
-
App內(nèi)接入熱更新SDK。
配置好appKey
app啟動會查詢是否存在新版本鸯旁,需要攜帶app標(biāo)識、app版本號量蕊、本地已存在版本等參數(shù)
客戶端sdk根據(jù)服務(wù)端給的數(shù)據(jù)铺罢,進(jìn)行下載、回滾或者不進(jìn)行操作残炮。
如果需要下載韭赘,下載完畢后,本地簽名校驗(yàn)文件完整性势就,然后存儲到本地
上報(bào)下載成功/下載失敗的信息給管理后臺
-
包管理服務(wù)
- 服務(wù)收到客戶端的請求后泉瞻,根據(jù)參數(shù)返回當(dāng)前app是否有新版本,以及新版本下載相關(guān)的信息苞冯。是否需要回滾等
-
App打開RN頁面
查找本地Bundle信息袖牙,加載最新版本
上報(bào)版本加載成功/失敗的信息給管理后臺
管理平臺發(fā)版流程:
-
js打包
設(shè)置目標(biāo)平臺:iOS/Android的Bundle包,
設(shè)置是否dev模式的包
-
發(fā)布
選擇發(fā)布的環(huán)境:feature/uat/beta(測試環(huán)境)
選擇投放的app版本:是一個區(qū)間抱完,比如投放到1.0以上的版本贼陶, 1.0-2.0之間的版本
-
上線
從已發(fā)布的版本中,選擇要發(fā)布的jsbundle。
必須是已發(fā)布過測試環(huán)境的包才可以操作上線碉怔,不允許直接上線
設(shè)置是否灰度
控制放量0%~100%
App應(yīng)用管理
整體方案設(shè)計(jì)為多app的應(yīng)用場景烘贴。接入sdk時(shí),必須要使用appkey作為標(biāo)識撮胧。應(yīng)用管理中要管理appkey的生成桨踪,以及app版本信息的管理。
Bundle包管理
新建Bundle: 創(chuàng)建bundle的入口
bundle名稱: 工作中芹啥,交流溝通的名稱
唯一標(biāo)識: 唯一id锻离,代碼中使用的名稱
入口組件名稱:bundle內(nèi)允許多入口
投放的app: 當(dāng)前bundle會投放到哪些app上
-
操作
查看詳情: 更多細(xì)節(jié)信息,包大小墓怀,更新時(shí)間汽纠,版本號、打包傀履、發(fā)布虱朵、上線、回滾等操作
編輯: 編輯基礎(chǔ)信息:git倉庫地址等
新建bundle
打包
[圖片上傳失敗...(image-92aa41-1712815885556)]
發(fā)布
[圖片上傳失敗...(image-6ebf8d-1712815885556)]
上線
[圖片上傳失敗...(image-4d65bb-1712815885556)]
存儲
條件下發(fā)
在發(fā)布一個包之前钓账,需要在小范圍內(nèi)進(jìn)行測試或者線上回測碴犬,比如特定某個 iOS 版本或者特定某個用戶;在驗(yàn)證通過后再進(jìn)行全量用戶的下發(fā)梆暮。這時(shí)可以用到條件下發(fā)服协。
分發(fā)平臺在發(fā)布包時(shí)可以選擇使用條件下發(fā),除上傳包外啦粹,還可以填寫條件語句偿荷,只有滿足條件的設(shè)備才會獲取到最新版本的包。
特定版本
設(shè)備id
用戶ID
當(dāng)包的下發(fā)狀態(tài)處于條件下發(fā)唠椭,且相關(guān)參數(shù)與 SDK 上報(bào)參數(shù)中的條件一致時(shí)遭顶,才會將包發(fā)送給該 SDK。
白名單
支持設(shè)置白名單泪蔫,只有白名單里的用戶id 或者設(shè)備id才可以獲取最新版本的包
設(shè)備白名單
用戶白名單
數(shù)據(jù)統(tǒng)計(jì)
提供分日棒旗、分 App、分版本的包分發(fā)數(shù)據(jù)統(tǒng)計(jì)功能撩荣。
SDK 設(shè)計(jì)
SDK只需實(shí)現(xiàn)版本的查詢和 bundle包的下載即可铣揉。
以 iOS 為例:
客戶端 SDK 啟動時(shí)會發(fā)請求詢問服務(wù)端,根據(jù)服務(wù)端返回?cái)?shù)據(jù)進(jìn)行相應(yīng)處理餐曹」涔埃客戶端 SDK 會保存下載到的jsbundle包,避免重復(fù)下載造成的流量損失台猴。具體流程如下:
App 啟動同時(shí) SDK 也啟動朽合,并發(fā)送查詢請求給服務(wù)端俱两,請求攜帶 App 標(biāo)識、App 版本號等參數(shù)曹步;
服務(wù)端根據(jù)收到的請求判斷下發(fā)該app對應(yīng)的配置信息宪彩,包括包版本信息、下載地址和其他一些信息讲婚∧蚩祝客戶端 SDK 根據(jù)接口返回的數(shù)據(jù)判斷進(jìn)行下載、回滾或不進(jìn)行任何操作筹麸;
如果未返回任何信息活合,說明不存在新版本需要下發(fā),此時(shí)客戶端 SDK 不進(jìn)行任何操作物赶;
如果返回的配置信息中白指,包的版本號等于本地生效腳本的版本,說明客戶端保存的包已是最新的酵紫,SDK 直接執(zhí)行本地保存的包侵续;
如果返回的包信息中,包的版本號不等于本地生效腳本的版本憨闰,說明服務(wù)端有新的修復(fù)包發(fā)布,或發(fā)生了回滾操作需五,客戶端 SDK 判斷本地是否存在該版本的包鹉动,存在時(shí)直接執(zhí)行本地包;不存在時(shí)發(fā)起下載請求獲取最新的包宏邮,并在本地緩存泽示,然后執(zhí)行。
成本
從三個方面了對比成本問題
使用第三方那個付費(fèi)服務(wù)
私有化codepush
完全自研
應(yīng)用數(shù)
共計(jì)118個獨(dú)立的功能模塊蜜氨。我們按照60%的業(yè)務(wù)使用react-native開承載械筛,我們簡單把每個模塊劃分為一個應(yīng)用(實(shí)際可能比模塊數(shù)多),預(yù)計(jì)需要71個應(yīng)用飒炎。
pushy最大支持20個應(yīng)用埋哟。無法支持,pass
Codepush 根據(jù)應(yīng)用數(shù)量收費(fèi):40/月
codepush | codepush私有化部署 | 完全自研 | |
---|---|---|---|
成本 | 2840$/月 | 服務(wù)器成本 少量人力開發(fā)成本 | 服務(wù)器成本 人力開發(fā)成本 |
優(yōu)缺點(diǎn) | * 成本較低 * 功能受限于codepush郎汪,無法擴(kuò)展 * 源碼需要上傳到微軟服務(wù)器赤赊。存在一定的信息安全風(fēng)險(xiǎn) |
* 成本在于人力成本和服務(wù)器成本 * 前期投入低,功能可漸進(jìn)式演化迭代煞赢,更符合自身需求 * 源碼無外泄風(fēng)險(xiǎn)抛计,信息安全的風(fēng)險(xiǎn)較低 |
* 成本在于人力成本和服務(wù)器成本 * 前期投入多余私有化部署,功能可漸進(jìn)式演化迭代照筑,更符合自身需求 * 源碼無外泄風(fēng)險(xiǎn)吹截,信息安全的風(fēng)險(xiǎn)較低 |
私有化部署和完全自研的工作量對比
私有化部署 | 完全自研 | 備注 | |
---|---|---|---|
客戶端SDK(提供版本管理和下載功能) | 使用codepush SDK | 自研SDK | 工作量: 私有化部署<自研 |
* 需要花時(shí)間研究codepush的sdk * 熟悉使用方法和私有化接入方式 * android 1人 * 5瘦陈,iOS1人 * 5 |
* 需要設(shè)計(jì)版本管理和下載方案 * 開發(fā)sdk并接入 * android 1人 * 15,iOS1人 * 15 |
||
存儲服務(wù)(提供jsbundle包的存儲和增刪改查等功能) | 可通過修改源碼的方式波俄,設(shè)置自己的服務(wù)器晨逝,快速部署,開發(fā)成本低 使用nodejs實(shí)現(xiàn) |
可自己設(shè)置服務(wù)器弟断,開發(fā)成本高 可自主選擇編程語言 |
私有化部署<自研 N >> 5 |
服務(wù)器資源預(yù)估: 以71個應(yīng)用為標(biāo)準(zhǔn)(當(dāng)前2個應(yīng)用): * 單應(yīng)用的bundle大小600k以內(nèi)(一般90k-300k就足夠了) * 單應(yīng)用全年迭代以10次估算(實(shí)際單一應(yīng)用全年應(yīng)該不至于迭代這么多) * 開發(fā)測試階段的發(fā)版咏花,按照50次為標(biāo)準(zhǔn),(實(shí)際應(yīng)該會在10-40次之間) * 上線按照每次需要緊急修復(fù)2個版本為標(biāo)準(zhǔn)阀趴。共上線3次昏翰,(大部分應(yīng)該不需要緊急修復(fù)) 合計(jì)全年占用存儲資源: 71 * 600K * 10 * (50 + 3)= 22260000kb = 21738.2812Mb = 21.22879Gb |
|||
* 熟悉源碼,修改相關(guān)設(shè)置項(xiàng) * 部署工作 * 后端:1人 * 2天 |
* 開發(fā)供sdk使用的接口 * 開發(fā)用戶管理刘急、應(yīng)用管理棚菊、版本管理、編譯叔汁、打包统求、發(fā)布、上線据块、回滾 * 部署 * 后端:≥1人 * n天(具體待評估) |
||
可視化管理后臺 | * 需要自研 * 前端: 1人 * m天 |
* 需要自研 * 前端1人 * n天码邻;后端1人 * n天 |
私有化部署 =自研 m > n |
優(yōu)缺點(diǎn) | 功能簡單; 開發(fā)成本低; 可通過二次開發(fā)的方式另假,拓展更多功能像屋; |
功能強(qiáng)大; 開發(fā)成本高; 后續(xù)可以拓展更多功能; |