從未降級的搜索技術-Hippo在線服務調度系統

jopen 10年前發布 | 14K 次閱讀 Hippo

        很久很久以前,有一個 PE 叫川小生,有一個開發叫子小嘉。雙 11 前,他們按照業務的要求給天貓準備了 14 倍余量,給主搜準備了 1 倍余量。結果 11 號上午流量漲勢喜人啊,嗖嗖往上漲。川小生和子小嘉說不對啊,怎么主搜漲這么厲害天貓只漲 4 倍呢,川小生掐指一算,干,到晚上主搜就掛了啊。倆人慫了,把天貓機器遷一點給主搜吧。于是改 clustermap 下機器,發 binary,發依賴數據,發全量,追增量,起進程,改 clustermap 加機器,一通折騰一個半小時過去,總算有驚無險。滿心期待到了晚上,主搜流量卻木有來,有木有,木有來啊。。。

        上面是一個發生某年雙 11 的一個真實的關于搬機器的故事, 好像每年的雙 11 總會發生點超出我們預期的事情,而每次系統變動又總是讓人膽戰心驚。2014 年的雙 11 我們內心變得很平靜,這些事情再也不需要咱自己去干了,因為咱有了自動化的解決方案——來自引擎調度系統小組的 Hippo。

        一、來自一線的訴求

  • PE/App Ops 同學的訴求
  • 業務安全-健壯的系統-不要隨便回收應用的機器-及時完整系統反饋/監控
  • 系統利用率低-資源管理/復用-快速方便的調整應用資源(負載高時擴容、負載低時減機器)
  • 搗騰機器太麻煩、大促搬機器累死的呢-集群資源統一管理
  • 太復雜了-簡單易理解,系統解耦(避免牽一發而動全身)-系統可視化
  • 熬夜上線可不可以沒有-系統級別支持灰度/平滑上線-支持方便快捷的部署/發布系統
  • 上線麻煩,要解決太多依賴-自動部署解依賴
  • 業務/系統開發同學的訴求
  • 上線不求人,不要排期-更加高效的上線流程-系統解耦,不要相互約束-流程(自動化)友好
  • 不要搭環境,不要搞機器-屏蔽運維操作、提供自動運維服務
  • 方便 debug-可重入/可復現的系統環境
  • 簡單應用不要開發-提供默認的調度、支持非侵入式接入、輕量級
  • 復雜應用支持自定義調度-支持多層調度
  • 隨時可用的測試環境-共享測試集群
  • 快速測試反饋-集成測試自動流程
  • 熟悉的開發語言

        這些訴求是我們與相關同學長時間深入溝通拿到的(真是很難感覺到幸福啊),轉換到對我們的調度系統的需求:集群集中管理、資源調度、應用托管、高效自動部署/變更、應用安全、應用隔離。

        二、為什么造輪子

  • 業內系統
  • Borg、Omega(Google)
  • Autopilot Microsoft
  • ARK/IDLE/Matrix(Baidu)
  • TBorg、Torca (Typhoon.Tencent)
  • 有規模應用開源系統
  • Yarn (Hadoop)
  • Condor、HTCondor (CS.WISC)
  • Mesos (推ter)
  • 公司內部系統
  • JAVA 流 (T4,YARN 衍生系統)
  • FUXI (Apsara)

        筆者最早接觸的是 Condor/HTCondor,搞過網格計算的同學應該比較了解;Goolge 的 Borg 應該算是一開始借鑒了很多 Condor 的東西,Omega 則是在解決 borg 的單 master 調度的瓶頸問題;Tencent 的 Tborg/Torca 則是和 Borg 系統有很深的淵源;Yarn 和 Mesos 應該是被更多的人所熟知,都支持多種計算框架;對 AutoPilot 的認知更多來自于相關的論文;Baidu 的系統其實蠻有意思,特別是 IDLE(有個組件可以隨意種植在任何機器上,當機器空閑的時候則調度一些低優先級并且可以隨時K掉的計算任務上去執行,而且他們的 PE 人員身背機器利用率的 KPI,大家都求著調度任務上去,這和咱們的現狀完全是兩樣);FUXI 和 T4 是集團內的系統,大家想要了解可以在內網找到他們。

        搜索中心的在線系統基本都是基于 C++ 的,跑在 Yarn/JAVA 上不免顯得有點重了,所以 Yarn 其實在意開始就被我們淘汰掉了,但我們重點研究了它的協議。曾經一度離我們最近的是 FUXI 和 Mesos,再看看我們在線服務系統的基礎要求:

  • 高可用性。時刻需要保證完整性,對應到對資源分配的需求就是分配穩定不能在不保證服務完整性的情況下回收機器
  • 資源分配的穩定性,在線服務一般遷移成本比較高,需要比較穩定的分配,不到萬不得已的時候不能遷移服務
  • 快速變更能力。搜索負責從海量數據進行召回,一般依賴的數據都很大(現在線上單機典型的數據大小,Binary 包:700M;Hadoop,jvm:1G;AliWS 詞典:500M;詞典補丁:100M;索引數據:40G;增量索引:1G;前后臺類目映射表:10M;算法模型數據:4G),如何快速的安裝部署轉移是一 個很大的難題

        我們要的不僅僅是一個資源管理統一調度系統,而是支撐整個在線服務系統的一攬子工程。回到資源管理上來,FUXI 和 Mesos 在資源回收協議上都是強制回收的,異常情況下會影響服務的完整性,這是不能接受的。對于二進制包/依賴數據的分發 FUXI 和 Mesos 都是集中式的拉取對于在線的多 replica 效率沒法滿足需求。另外考慮到服務遷移的成本,我們希望調度框架是非植入的(目前 FUXI 在不繼承框架的時候只能進行簡單的進程起停,不能監控服務進程的健康),能夠做到應用的無痛遷移。針對這些問題,我們與 FUXI 的同學做過深入的交流,對于我們的這需求暫時還不能滿足;Mesos 來講,評估過后發現如果我們去改造 Mesos 的成本并不比全新開發來得低,至于 Docker 流的 Kubernetes 以及集成到 Mesos 那已經是后話了,Hippo 啟動的時候 Docker 還沒那么火。最終我們的 Hippo 定位于專注在線服務管理及支撐,并把資源管理管理做薄,一旦 FUXI 成熟我們可以將整個 Hippo 系統跑在去,順帶也將上面的服務平滑遷移到云上(是的,上了 Hippo 咱們服務就提前上云了),我們的目標是盡量不要重復造輪子。

        三、Hippo 系統架構

        Hippo 實現采用兩層系統架構:一層(Master)負責資源管理以及核心調度器調度,二層(AM)為具體應用調度。各應用可定制開發或者使用默認調度器調度。

從未降級的搜索技術-Hippo在線服務調度系統

        Hippo 系統采用典型的 master-slave 中心節點架構,包含兩個角色:

  • master 服務器端,負責 hippo 中所有資源的管理以及全局資源調度/應用管理,在運行時多個 master 以熱備方式保證可用性,主要包括下面幾個子模塊
  • slave manager, 負責所有機器(slave, 每個 slave 可以分為多個 slot,每個 slot 對應了一組資源)的管理(確定了 Hippo 集群的管理域)、收集維護各個客戶端節點的資源信息
  • app master manager, 負責所有應用調度器的管理和調度(針對簡單應用可以直接調度應用本身節點)
  • resource manager, 負責管理系統所有資源以及為每個應用分配資源(以 slot 為基本管理和調度單位,目前 slot 通過靜態劃分、后續會支持通過需求動態生成)
  • slave 客戶端,負責管理某一臺具體的物理機,它主要完成下面幾個功能
  • 客戶端資源收集
  • 應用部署/安裝/運行/監控/管理支持
  • 提供接口給 app master 進行業務進程管理,具體調度任務的執行者
  • 單機資源管理,分 slot 維護,支持多應用復用物理機并保證應用的完整性和獨立性

        四、Hippo 核心特性

        Hippo 作為服務器與在線服務應用的中間層,其核心的功能則是向下抽象管理資源、向上抽象在線服務需求并保證兩者有效安全的銜接。這一節將按照這個思路來簡單介紹一下 Hippo 的核心特性。

        4. 1 資源管理

        4. 1.1 資源

        資源是對 Hippo 中 Slave 這些工作節點服務能力的一個抽象。SCALAR 數值型(用于描述 CPU 核數/MEM 大小/DISK 大小/網絡帶寬等可計量資源)、TEXT 文本型(用于描述不可計量資源,比如描述磁盤是否是 SSD)。其中 CPU/MEM 作為系統內置資源由 Hippo 自動探測,其余資源由外部設置。Hippo 借鑒 FUXI 對資源的描述支持任意的虛擬資源,特別的是 Hippo 引入了一個“EXCLUDE_TEXT ”排他資源類型用于對資源可申請對象的約束。Hippo 支持動態修改 Slave 的自定義資源描述。

        4. 1.2  SLOT(槽)/機器分槽

        Hippo 以 SLOT 為粒度進行資源的管理分配,一個 SLOT 代表了一組資源組合。主要分為兩類:普通槽,主要分給普通應用使用,每個槽對有一個槽號(>=0 的整數)標識;系統槽,主要給 Hippo 自身內置服務組件使用,與普通槽的差別是它不占用邏輯資源,槽號為<0 的整數。

        一臺機器(slave)被加入 Hippo 的時候可以申明一組資源并需指定槽數 slot_count,Hippo 將 slave 劃分成 slot_count 個普通槽,這些槽均分 slave 上申明的數值型資源并繼承文本型資源(內置自動探測資源屬于數值型,會將 Slave 自動探測匯報的資源均分到每個槽),并自動分配 system_slot_count 個系統槽(系統槽個數在 Hippo 啟動時指定)。舉個例子,在一個配置了一個系統槽的 Hippo 系統中一個 32 核 64G 的機器分兩個槽的情形:
從未降級的搜索技術-Hippo在線服務調度系統
Hippo 目前只支持這種靜態分槽(資源切分)的方式,動態分槽的需求目前還不是很明確,后續會根據需求引入。

        4. 1.3 資源的申請/分配/回收

        應用對機器的需求全部抽象成資源需求,Hippo 支持多 TAG 全量資源申請協議。一般應用系統都存在不同的角色 ROLE,而每個角色對資源的需求也都會不一樣,比如一個典型的二層調度應用就至少包含兩種角色:應用 Admin(二層調度器)+ 應用業務 Worker,資源申請 TAG 則對應了應用 ROLE 的概念。每個 TAG 的資源需求描述支持或邏輯,比如某個 TAG 的資源需求描述可以是這個樣子{ {CPU3200, MEM 65536} or {MACHINETYPE_A71}}: 要求分配的 SLOT 的 CPU 大于等于 32 核并且內存大于等于 64G,或者分配的 SLOT 要有自定義的 MACHINETYPE_A7 資源。采用全量協議而不是 FUXI 的增量式協議主要原因有兩:一是全量協議實現簡單,不容易出錯;二是在線服務的應用數目與 FUXI 的 JOB 數目差幾個數量級,全量協議的資源消耗在今后很長一段時間都不會是瓶頸。

        Hippo 目前不存在應用優先級所以資源分配遵循最簡單的 FIFO 邏輯,采用二維打分機制來進行最終的分配,一維為資源分(根據請求與資源的最小滿足原則計算得分);二維為 Hippo 引入的“資源親近性”得分,“資源親近性”用于描述一個應用對某臺機器(SLOT)的“喜好”,Hippo 支持三種類型的親近性:_PREFER、_BETTERNOT、_PROHIBIT,這關系依附于三元關系組,分別表示“對應用 app 的 reourceTag 盡量分配 slaveAdrees 上的槽”、“對應用 app 的 reourceTag 盡量不要分配 slaveAdrees 上的槽”、“對應用 app 的 reourceTag 不能分配 slaveAdrees 上的槽”。同時為了更好控制,Hippo 給“資源親近性”加上了失效時間。

        Hippo 中 SLOT 的回收有兩個發起點:一是應用主動釋放;二是 Hippo 協議應用釋放。在 Hippo 上除了機器異常情況下可以強制下線機器外,不允許 SLOT 當前 Owner 以外的角色發起 SLOT 回收,以保證應用的安全。一個正常的機器回收邏輯 Hippo 中是這樣實現的:(1)將要回收的機器打上 offline 標簽,該機器上未分配出去的 Slot 就不能再被分配;(2)hippo master 要求使用該機器的應用回收對應的 Slot;(3)應用額外申請一批 Slot,將 Worker 遷移上去,保證服務的完整后主動釋放要求回收的 Slot;(4)Hippo Master 發現該機器上所有的 Slot 已經回收則標識該機器可回收。

        Hippo 的整體資源管理方案還比較初級,例如每次分配都追求局部最優并不能做到全局最優,后續會考慮抽象出更多的決策因子(比如包/數據分布)爭取提高 Hippo 的整體效率。

        4. 2 服務托管

        Hippo 系統內對在線服務做了最基礎的一層需求抽象—-進程組模型,進程組是在線系統的最小調度單位,我們可以以此為基礎構建更高層次的服務抽象。Hippo 的進程組模型由<依賴包,進程描述,依賴數據>這樣一個三元組來描述,一個進程組包含 0 個或者多個依賴包、0 個或者多個進程實例、0 個或者多個依賴數據,特殊的一個空的進程組在 Hippo 中也是支持的,它不執行任何操作只是持有資源。一個進程組運行在一個 Slot 上,Hippo Slave 提供接口給應用在一個 Slot 上啟動、停止一個進程組,Hippo 會根據應用提交的進程組描述自動進行包安裝、依賴數據拉取、進程啟動管理或者執行相應的退出流程。本章后面部分會分別針對依賴包,進程描述,依賴數據進行 一個簡單的介紹。

        4. 2.1 依賴包抽象與運行時支持

        Hippo 支持三種類型的依賴包格式:普通文件/目錄、RPM 包、壓縮包。其中普通文件/目錄與壓縮包需要是一個完整的可執行環境,Hippo 只負責將這些數據拷貝到當前應用的安裝目錄下,而對于 RPM 包,Hippo 首先會將包下載下來然后使用內置的 Ainst2 工具(一個強大的 rpm 包解依賴安裝工具,支持遠程并行安裝,目前我們團隊在維護)來安裝到相應的目錄。Hippo 中任何依賴包的變化都意味著進程組的重新啟動,可以把依賴包視為一種靜態依賴。任何一次進程組執行都首先從下載依賴包開始(下載主要分兩種方式,一種是通 過 yum,另外一種是通過 Hippo 內置的數據鏈式分發服務 DP2,因此包可以發布在任何 DP2 支持的數據源上),如果下包失敗 Hippo 會自動重試直到最后報告安裝包失敗。

        4. 2.2 進程描述抽象與運行時支持

        Hipppo 抽象了進程描述,包括進程的啟動方式(Daemon/非 Daemon)、命令行及參數、環境變量,Hippo 特殊的是可以對每個進程指定一個名字和一個 instanceId, instanceId 對應了一次顯示的啟動,Hippo 如果發現新提交的進程 instanceId 與當前運行的不一致則會重新執行一次(通常用于有變更需要進程重啟生效的場景)。所有的進程由 Hippo 啟動,對于非 Daemon 進程,Hippo 會保證其正常的執行一次;對于 Daemon 進程只要 Hippo 發現不存在就會重新拉起(啟動時會有重試次數限制,超過限制將直接報告失敗),并記錄失敗信息。

        4. 2.3 數據依賴抽象與運行時支持

        Hippo 內置了一個數據管理模塊,負責應用數據的自動拉取(使用 DP2 服務)及版本管理,應用層面不需要顯示的執行數據準備工作。針對在線服務一般依賴的數據比較多的特點,數據管理借鑒了 git 的全量 snapshot 版本管理模式同時借助 DP2 的增量傳輸協議高效的解決了數據依賴問題,通常數據管理先會把依賴的數據拉取到一個全局緩存然后再鏈接到應用的工作目錄。數據管理同時負責數據的生命周期 管理,自動清除過期的數據。當應用有數據變更時,只需要修改數據依賴描述并提交給 Hippo,Hippo 會反饋數據準備的狀態,應用一旦發現數據準備好重新啟動進程新數據即生效。

        進程組模型提供了解決服務托管的基礎支持,對于那些一維的簡單應用使用 Hippo 內置的 Global App Master 即可很好的工作,但是對于那些復雜的應用來講還需要自己編寫二層調度器,雖然 Hippo 現在提供了一個高度封裝的 SDK 但是門檻還是挺高。目前 Hippo 正在探索更高層次服務抽象,比如最近團隊正在開發的 App Framework, 而筆者最終希望能夠抽象出一個通用的服務模型(以及服務能力模型)通過簡單的配置就能完成服務的所有自動化調度(匹之于離線系統的 JOB 模型)。

        4. 3 服務安全保障

        由于 Hippo 調度的都是在線服務系統,所以應用的安全性(可用性)至關重要。簡單的從下面幾點看看 Hippo 是如何來保障應用安全的:

  • 代碼層級。Hippo 一直強調“非注入”,即不要求運行在 Hippo 上的程序要嵌入 Hippo 的任何模塊(特別是業務進程),業務進程的健壯性完全由業務系統開發自己決定。唯一存在代碼依賴在二層調度器使用 Hippo SDK(可以選擇使用原生 Proto 協議),包括后面可能引入的調度框架都只影響調度器,仍然保持對業務進程的零注入。
  • 運行時環境。包括:
  • Hippo 系統的可用性。Hippo 通過 Leader election 實現了多 Master 熱備;在部署上不跨機房很大程度能夠避免網絡割裂;決策保護,在出現一定 Slave 心跳丟失時 Master 停止決策。
  • 應用環境的穩定。分配方案持久化/決策安全/資源協商回收/進程托管監控/進程信息持久化/進程恢復。
  • 應用間隔離。由于現在需求不強烈(目前搜索中心的引擎基本都是單機獨占),所以暫時只做到了應用工作目錄的隔離。隨著 Hippo 上應用范圍的擴大,應用間隔離一定會實現,容器/Docker 等技術準備工作已經完成,Demo 開發發現公司的系統版本及安全策略導致現有的解決方案都不會太完美,暫時已經停止等待更好的時機。
  • Hippo 獨立升級。Hippo 系統升級不影響應用進程,Hippo 恢復后自動重新接管應用進程。Hippo 自身以及涉及到與應用的接口兼容性是 Hippo 開發的首要準則,出現重大變更時也會有協議轉換層保證平滑過渡。
  • 監控報警機制。目前做的一些工作包括:可視化展示、基礎監控體系對接、提供 BabySitter 擴展模塊支持等。未來我們會把應用相關的監控報警邏輯放到體系內來。

        五、Hippo 在線

        雙 11 前我們完成了多個機房的 Hippo 集群部署上線,將主搜和天貓的后臺引擎完全遷移上了 Hippo, 并且很好的的支撐了雙 11 需求。Hippo 過去時間主要精力在搭建基礎平臺,業務層面更多的關注了“自動化運維”的一些需求,在未來一段時間我們將主要關注在線服務抽象,針對系統應用開發人員提供 更高層次的抽象以降低業務遷移成本,目標是一年后 90% 的搜索機器(在線服務系統)跑在 Hippo 上。

                    <span id="shareA4" class="fl">                  
                        </span>
 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!