天天看點

這個夏天,配置項也要清清爽爽什麼是「驗貨寶」那女(運)孩(營)對我說,再再再來個新類目簡單點,新增類目的方式簡單點煙花易冷,輪子少造總結

作者:閑魚技術——尋弈

任何業務系統在高速成長的過程中都需要快速的疊代傳遞,驗貨寶業務也不例外。這個過程中不可避免的會在系統代碼中不斷引入「壞味道」。

下面我們來看看驗貨寶近期做的一個微小的優化和一些思考。

什麼是「驗貨寶」

這裡首先介(ān)紹(lì)一下閑魚的驗貨寶服務。

在閑魚購買數位産品、潮鞋、奢侈品包包等貴重物品時,買家可能會擔心買到假貨或者與賣家描述不符的寶貝,賣家也希望自己的優質寶貝能賣個好價格。

為了解決買賣雙方的信任問題,閑魚和專業機構合作,為所有的驗貨寶商品提供權威的驗貨報告。

當買家下單購買驗貨寶商品後,賣家将寶貝發貨至驗貨中心,驗貨中心出具驗貨報告後,買家可以根據報告決定購買或者不購買。

驗貨寶服務一上線就深受使用者喜愛,短時間内圈粉無數。

那女(運)孩(營)對我說,再再再來個新類目

驗貨寶上線也半年有餘,需求疊代速度也趨于平穩,得益于優良的整體架構設計,目前後端開發由我一個人即可 Cover 住。但在需求疊代的過程中還是有一些「痛點」,比如:我希望當營運同學後面不斷來找我新增類目時,我可以更快更簡單一點搞定。

驗貨寶目前首批上線支援的品類有:手機、平闆、筆記本、潮鞋、奢侈品包包、奢侈品腕表、奢侈品飾品、奢侈品服裝。後續驗貨寶服務還将覆寫更多品類,讓大家賣得舒心買得放心。

這個夏天,配置項也要清清爽爽什麼是「驗貨寶」那女(運)孩(營)對我說,再再再來個新類目簡單點,新增類目的方式簡單點煙花易冷,輪子少造總結

不同類目有着不同的驗貨費計算政策、不同的介紹頁 URL、不同的服務商、不同的可更新的價格區間(指定價格段的商品才可以更新驗貨寶服務)、不同的内部 Code 等等。當然這些大部分内容是通過配置進行管理的,但配置散落在多個系統、多個 key 中,還有一部分是寫死在代碼中的。

配置分布在多個系統中主要是因為不同配置系統側重有所不同,比如有的配置系統面向開發同學、有的面向營運同學;寫死在代碼中主要是如一些全局的常量 Code 需要打到依賴的 JAR 包中。寫死的配置帶來的問題是上線新的品類需要進行服務端代碼釋出,會受節假日、封網等的影響,釋出周期長、不夠靈活。

其實這個一個常見同時也容易忽視的場景,一條鍊路中相關聯的配置需要收口到一個「原子配置」(指的就是一個最小的下發機關)中,配置項過多且分散可能帶來的諸多負面影響:

  • 增加維護成本:變更流程繁瑣,需要修改多個配置;
  • 易出錯:容易出現錯配、漏配而不自知的情況;
  • 變更時間延長:每個配置都需要修改、走流程審批等;
  • 一緻性問題:如果一條鍊路多個配置有時序依賴,那麼配置系統下發的延時可能引發一緻性問題,需要額外的手段保障最終一緻性,但原子配置就不存在這個問題。

為了優化這個問題,同時為了支撐後面新類目能夠快速上線,驗貨寶剛剛做了個專項優化:配置的歸一化改造。目标是新類目上線免釋出,同時配置統一按類目收口一處。

簡單點,新增類目的方式簡單點

首先從兩大主要鍊路入手梳理:

  • 商品更新鍊路
  • 訂單履約鍊路

整個鍊路涉及多個應用,配置的類型也多種多樣:String、Boolean、Map、Integer 等等。現有「Mach 雲投放平台」剛好可以滿足這個配置中心的需求。

Mach 提供獨立的配置定義和配置執行個體能力。配置定義采用 JSON Schema 對配置内容進行類型限制,配置執行個體可以建立不同投放時間段、不同優先級、不同環境的多個執行個體。

這裡我通過一個簡化的例子說明下這條鍊路,比如我梳理出來每個類目應有這 3 個配置:

  • 驗貨寶服務說明頁面 URL:字元串類型
  • 應收取的驗貨費金額:數值類型
  • 該類目可以更新驗貨寶服務的分類:字元串清單類型(這項我解釋一下,是用來配置多個分類如籃球鞋、闆鞋、帆布鞋等都可以開啟驗貨寶潮鞋類目驗貨服務)

那麼我在 Mach 上建立一個新配置:「驗貨寶配置集」,首先定義 JSON Schema:

這個夏天,配置項也要清清爽爽什麼是「驗貨寶」那女(運)孩(營)對我說,再再再來個新類目簡單點,新增類目的方式簡單點煙花易冷,輪子少造總結

然後建立一個配置的執行個體,設定生效時間區間、優先級等資訊。最後就填這 3 個配置的具體内容,Mach 會根據配置項的資料類型生成對應的 GUI 填寫頁面,比如 string 類型就是一個文本輸入框;array 是一個帶 + 按鈕的文本框清單;number 類型是一個帶數值校驗的文本輸入框。

這裡例子就不貼頁面截圖了,用文本示意下:

  • introductionPageUrl: www.taobao.com/yanhuobao/introduction-page.html
  • platformServiceFee: 39
  • cateIdUnderScene: [123, 234, 345]

OK,現在我們就可以通過 Mach 的服務接口拉取這個配置資訊了,我們可以從接口擷取到這個配置執行個體的 JSON 字元串,通過 fastjson 就可以解析到對應的配置内容了。

當然我們對配置定義的結構和實際使用的資料結構不一定完全一緻,我們會将以上配置解析為一個包含如下 3 個變量的配置 DO 對象:

這個夏天,配置項也要清清爽爽什麼是「驗貨寶」那女(運)孩(營)對我說,再再再來個新類目簡單點,新增類目的方式簡單點煙花易冷,輪子少造總結

線上業務 QPS 非常高,同時這些配置不要求實時擷取最新值,是以我們在本地做一份緩存,當然将解析好的 ConfigDO 對象儲存下來是最好的選擇。

煙花易冷,輪子少造

一個應用中會引用非常多的 Mach 配置,每個配置解析出來的 DO 資料結構各不相同,但如果每處使用都自己緩存勢必造成重複開發和資源的浪費。那麼我們這裡順帶引入了一個通用的配置緩存池。

這個夏天,配置項也要清清爽爽什麼是「驗貨寶」那女(運)孩(營)對我說,再再再來個新類目簡單點,新增類目的方式簡單點煙花易冷,輪子少造總結

緩存池采用的是 Guava 的 LoadingCache,通過抽象出一個 ConfigValueParser,各個配置使用者可以實作其對應的解析邏輯。

這個夏天,配置項也要清清爽爽什麼是「驗貨寶」那女(運)孩(營)對我說,再再再來個新類目簡單點,新增類目的方式簡單點煙花易冷,輪子少造總結

在 parseConfig 實作解析邏輯,傳回上面提到的配置解析後的 YhbConfigDO 對象即可。

在使用的時候就可以直接擷取:

YhbConfigDO yhbConfigDO = configMachReader.get(CONFIG_MACH_ID);

總結

本文通過一個驗貨寶近期的一個配置歸一化的優化介紹了産品鍊路中相關聯的配置分散可能會産生的問題,以及優化方案。

希望能對大家有所幫助。