1. 程式人生 > >從移動端的配置說起

從移動端的配置說起

出了什麼問題

大多數客戶端都有遠端配置的功能和需求,專案規模由小到大以後,對客戶端動態配置的需求就會迅速增加。就會出現新的問題和需求。

  • 配置項逐漸增多,配置內容大小逐步增大
  • 客戶端版本逐漸曾多,版本之間的配置差異較大,配置管理混亂,牽一髮而動全身
  • 運營和產品對業務配置的需求逐漸增加,需要有獨特的配置關聯邏輯
  • 配置不斷龐大,下發到客戶端的時候需考慮流量問題
  • 配置服務端考慮併發問題
  • 配置動態下發,考慮不同的更新策略,考慮安全性

歷史及現狀

可能很多移動端的開發者都有這樣的經歷: 通過某一個介面,獲取某一業務功能的配置資訊,有時候需要根據業務觸發的邏輯,在不同的時機呼叫介面,獲取配置,又有些時候需要把客戶端的一些資訊,如版本號、時間、上次的快取等等,傳入介面獲取最新配置,這其實就是最簡單的遠端配置需求,根據配置相關條件,通過不同的更新策略,獲取遠端配置。

1.0階段

設計介面如下:

$ curl https://api.xxx.com/v0/configuration/getMessageConfig?appVersion=1.0.0&platform=iOS&messageType=1 \
-H "SS-Cache-Version: XXXXXXXXX"

{
	"code":"0",
	"result":{
		"config_value":"******",
		"cache_version":"******"
	}
}
複製程式碼

通過不斷開發新的介面,滿足各個業務線對配置功能需求。 優點:需求較少的時候,開發特別快 缺點:客戶端需要不斷開發新的API呼叫,服務端則需要不斷開發新介面,配置與客戶端的關聯資訊發生變化,API則需要進行升級,而客戶端存在多版本並存的情況,老版本API也無法下線,佔用服務端資源。

2.0階段

為減輕服務端開發依賴,有的開發者通過使用第三方開發平臺進行配置分發。 例如,使用umeng的線上引數進行遠端配置

優點: 無需服務端開發,第三方實現SDK與其服務端的通訊,不需要做客戶端開發

缺點: 無法與客戶端資訊做相關,只能通過約定配置引數名稱例如 配置項名稱+平臺名稱+客戶端版本作為配置項名稱,做硬關聯,大量生成重複配置項。無法控制更新策略。業務相關配置放置在第三方平臺,無法保證資料安全。

3.0階段

由此前的經歷和需求痛點,我們設計出新的移動端配置中心。 主要有如下功能

  1. 支援配置客戶端資訊與配置項相關,做到不同的客戶端獲取不同的配置項
  2. 支援配置增量更新
  3. 支援客戶端配置加密下發,保證安全
  4. 提供統一後臺配置介面,方便進行配置的管理
  5. 做到配置更新,主動推送到客戶端
  6. 支援配置回滾,刪除恢復

解決思路

根據以上需求,整體方案的解決思路可以是如下這樣:

  1. 移動端開發遠端配置元件,用於獲取最新的後端配置
  2. 客戶端與介面互動的時候,將諸如appid(存在對個應用)、appVersion、platform、channel(渠道)、systemVersion等基礎資訊傳入介面,方便配置項與其關聯
  3. 客戶端與介面互動的時候,支援全量更新,支援通過生成增量包進行增量更新
  4. 服務端與客戶端進行資料傳輸的時候,進行通訊資料加密
  5. 對於服務端,客戶端提供定時配置同步策略,服務端通過推送和長連線通訊主動推送配置
  6. 配置項後臺的增刪改查,都採取版本疊加,而不是重新覆蓋,支援回滾與刪除回覆
  7. 通過標籤系統,提供更靈活的配置項與客戶端的匹配關係

涉及方面

有了大概的解決思路以後,可以對涉及到的方面進行整體盤點,其實這也是移動端基礎設施的摸查,涉及以下幾個方面:

  • 客戶端配置元件,與配置中心互動,獲取配置資訊,定時輪詢更新策略,記憶體快取與本地持久化配置資訊,增量包應用,接收服務端推送事件
  • 配置中心,提供對客戶端獲取配置的API介面服務,介面支援根據客戶端資訊和標籤返回增量資料包/全量更新包
  • 後臺管理系統,提供應用管理和配置管理,支援新建配置,修改配置,回滾和刪除配置
  • 認證服務,客戶端通過認證服務以後,獲取通訊管道加密的會話金鑰,提供介面資料加密功能
  • 標籤系統,提供對客戶端、裝置、使用者等多個維度的標籤設定和獲取服務
  • 訊息中心,提供根據標籤系統,將配置更新的事件推送到客戶端
  • 定時任務系統,提供定時服務,將配置生效、推送配置等設定為定時任務

整體設計

API設計

客戶端與配置中心進行API互動,介面定義如下: queryConfiguration 入參:

  • clientInfo,包含appid、appVersion、platform、channel等
  • cacheInfo
{
	"clientInfo":{
		"appid":"***",
		"appVersion":"1.0.0",
		"platform":"1", //1為iOS 2為Android
		"channel":"AppStore"
	},
	"cacheInfo":[{
			"configName":"routerConfigMap",
			"version":"*****"
		},
		{
			"configName":"conditionConfiguration",
			"version":"*****"
		}
	]
}
複製程式碼

返回值:

  • configurationData,一個數組,包含配置項全量或者增量資料包
code 含義 備註
0 增量包 返回增量包資料
1 全量資料 返回配置全量資料
2 已刪除 表示該配置項已刪除
{
    configurationData:[
        {
            "configName":"routerConfigMap",
            "version":"*****",
            "code":0,
			  "hash":"*****",
            "patch":[]
        },
        {
            "configName":"orderActivity",
            "version":"xxxxxx",
            "code":1,
			  "hash":"*****",
            "value":"xxxxx"
        },
        {
            "configName":"conditionConfiguration",
            "version":"xxxxxx",
            "code":2
        },
    ]
}
複製程式碼

客戶端與API互動流程圖

配置中心管理平臺

App管理平臺

配置平臺

配置管理後臺,提供對應用的管理與配置項的管理,配置項與基本客戶端資訊關聯。 配置項儲存與客戶端資訊進行關聯對映,關係有OR和AND兩種,每個配置項設定關聯條件。例如配置項的關聯條件為:

configId <—> appId AND appVersion AND channel AND platform OR tag

新建、更新或者刪除某一配置,可以設定定時生效,Job系統會定時執行操作,並呼叫訊息中心,按照關聯條件,進行推送通知給客戶端,客戶端接到更新事件後,再呼叫API介面完成配置項更新。

服務端查詢配置項流程

這個流程裡有三個關鍵點:

  1. 根據clientInfo查詢匹配的配置列表,其中,AND關係和OR關係,需要通過構建一個配置id與條件的字典表,查詢的時候將AND或者OR的條件相關的配置id全部查詢出來,然後進行AND計算(取交集),OR計算取並集,其中appVersion是一個範圍,例如設定某一配置項的appVersion為”<=2.3.0 & >=2.1.0”, 根據語義化版本,進行單獨匹配,語義化版本 2.0.0 | Semantic Versioning的規範請詳細檢視文件
  2. 如果客戶端上傳有cacheInfo,將快取的配置id列表上傳,那麼,根據條件查出的最新配置id列表為A,上傳的快取配置id列表為B,分別計算出A與B的交集,逐個對比hash值,算出增量包,再算出屬於A但不屬於B的部分,屬於新增配置項,做全量包,再算出屬於B不屬於A的,屬於要刪除的部分。進行上述計算,只需要定義一套陣列的交集、並集與補集的計算,就可計算出結果。
  3. 生成增量包的時候,需要根據客戶端配置id和對應hash值,找到舊版本的配置項,再跟最新的配置項做文字對比生成增量包。文字增量演算法有google官方實現的一套:GitHub - google/diff-match-patch: Diff Match Patch is a high-performance library in multiple languages that manipulates plain text.

推送更新訊息

這個比較簡單,通過後臺增刪改查的配置項,根據其標籤和客戶端資訊,使用訊息中心,將更新事件靜默推送到裝置,而裝置客戶端資訊和標籤,與裝置唯一標示的繫結關係,在標籤系統維護。

總結改進

新的配置中心,滿足了現階段的需求,通過將配置項的關聯條件抽象成標籤,再加上增量更新,滿足了節省流量的需求。 未來還有進一步改進的空間:

  1. 配置後臺通過jsonschema來效驗配置的格式,方式配置錯誤
  2. 客戶端的配置元件改善通訊方式,使用推拉結合的方式,目前的推送基於訊息中心,未來可以使用UDP+心跳方式維持客戶端與服務端的資料同步
  3. 實現更多的更新發布場景,例如,更新配置項,可按照一定比例,逐步進行灰度更新,失敗可回退,提高可用性

多謝您花費寶貴的時間閱讀,希望能夠與大家多多交流