劉偉 360雲計算 html
咱們發現公司的服務器cpu, memory等資源利用並不充分;若是可以充分利用這些機器上的空閒資源同時又能保證業務服務的正常運行,將會節省很多的機器資源;因此咱們研究了Mesos來構建多任務調度系統。接下來就爲你們介紹下咱們的Mesos系統。
PS:豐富的一線技術、多元化的表現形式,盡在「HULK一線技術雜談」,點關注哦!java
公司內部的雲平臺爲各個業務線提供了大量的實體機和虛擬機來運行業務的服務,通過統計發現,這些分配給業務的機器cpu, memory等資源利用並不充分;node
若是可以充分利用這些機器上的空閒資源同時又能保證業務服務的正常運行,將會節省很多的機器資源;python
一提到多任務運行和調度,大部分人可能首先都會想到Kubernetes(k8s) + Docker, 跑起來如清風拂面, 順暢無比。然而咱們的業務機器大部分爲centos 6.2, linux kernel 2.6的環境,而docker的運行須要Linux kernel的版本是 3.10+
(可參考: https://docs.docker.com/engine/faq/#how-do-i-connect-docker-containers)
由於想利用業務正在使用的機器,又不能影響現有已在跑的服務, 因此不能升級內核, 不能重啓機器,顯然k8s這條路走不通;linux
還好,這個世界老是提供給咱們多樣的選擇,除了Kubernetes(k8s) + Docker, 咱們還有mesos;c++
先放上官方網站, 上面有很詳細的說明;
http://mesos.apache.org/
簡單來講,Mesos就是用於整個計算中心的操做系統,它統一管理計算中心全部機器的cpu, memory, disk, network等計算資源,按任務所需分配資源,調度任務,支持故障轉移等等;docker
上面架構圖的簡要說明以下:apache
- 各個Agent上報自已的計算資源給Master;
- Master給各個二級調度框架Framework發送resource offer;
- Framework將其上等待調度的task與收到的resource offer做匹配,反饋給Master;
- Master將相應Framework反饋的task和resource offer發送到對應的Agent;
- Agent使用Executor來運行task, 並限定資源使用;
在Mesos上能夠運行Spark, Storm, Hadoop, Marathon等多種Framework;json
官方文檔:
http://mesos.apache.org/documentation/latest/architecture/;
針對任務隔離這塊, Mesos除了支持docker容器技術,還提供了它本身的Mesos Containerizer, 這正是咱們所須要的.其實Mesos Containerizer目前也是利用Linux Cgroup做資源限制, 用Linux namespace做資源隔離.
Mesos Containerizer:
http://mesos.apache.org/documentation/latest/mesos-containerizer/centos
咱們的多任務調度系統須要解決的幾個問題
各組件簡介:
1.1 主體仍是Mesos master + Mesos agent;
1.2 二級調度框架使用的是Marathon;
1.3 在部署了Mesos agent的機器上同時部署monitor用於實時監控和調整Agent的可用計算資源;
咱們採用的是Mesos 1.4.1版本,用C++11編寫,Mesos項目自己很是龐大,依賴庫必然也不少,解決這些運行依賴問題首當其衝;
部署原則就是不改變,不污染所部署的機器環境,針對libstdc++和其餘一些so, 咱們不會將其安裝到例如/usr/local/lib這樣的系統目錄, 而是在打包時採用動態更改可執行程序的rpath的方法,使其運行時從咱們的安裝目錄加載相應的so庫, 具體做法就是
- 咱們將mesos運行所須要的全部lib文件都集中放在libs目錄下;
- 編譯出來的mesos可執行文件,使用patchelf來更新rpath路徑,指向咱們自已的libs目錄便可;
- patchelf這個工具能夠在不影響可執行文件運行的前提下,修改其elf文件結構中的某些屬性值,具體可參考:https://nixos.org/patchelf.html
這樣部署完,Mesos agent只是一個單獨的目錄,卸載只須要停掉進程,刪除目錄就好;
說一下編譯過程,雖然官網上已經介紹得比較詳細,但在編譯過程當中仍是會遇到一些問題:
自行開發了Monitor程序,和Agent一同部署在業務機器上,週期性的監測機器上可用資源和Agent自己所用資源;
Mesos爲咱們提供了動態資源保留這個超實用的功能,能夠限制Agent當前針對某個Role可使用的計算資源:
Monitor的監控評估結果就是當前Agent可使用的計算資源;
本想着到這裏這個問題就結束了,測試時發現Agent並不能在線實時調整這個動態資源保留,須要在配置文件時更新好當前可以使用的動態資源,而後重啓Agent;
重啓Agent是咱們不能忍受的,所以咱們修改了源碼,經過http接口在線調整動態資源保留, 這部分其實不難,mesos http接口定義十分清晰,依葫蘆畫瓢就行了.
task的部署目前咱們採用Marathon,上手簡單,功可以用; 若是須要更靈活的調整策略,可能就須要本身開採框架或基於某一框架二次開發了;
task實際上是有重要,緊急之分,佔用資源也不盡相同。對於重要緊急任務,爲了保障任務的更好運行,咱們會利用Mesos attribute,在調度任務時讓特定任務只跑在具備特定attributes的agent上, 這就須要爲每一個mesos agent設置相應的attributes;
遇到了一樣的問題,mesos不能在線動態調整attributes :-(, 其實也比較簡單,稍微梳理下mesos源碼結構,改起來不難;
還有一個問題,attributes是動態調整的,agent若是重啓了怎麼辦?咱們爲此部署了etcd集羣來管理,每臺agent都是etcd上的一個node, 經過etcd提供的http接口更新其attribrtes, agent會週期性的從etcd上同步;同時各agent 上的attributes信息也很容易從etcd上得到;
直接操做etcd, 刪除某臺agent上的attribute, 那依賴於這種attribute部署的任務會自動別調度走,再也不在這臺agent上運行;
task隔離問題,針對cpu和memory,mesos都是經過cgroup來完成,對於cpu的限制, 咱們使用cfs方式,前提是須要判斷當前kernel是否支持.對於disk的限制,目前mesos使用的是du命令週期性檢測的方式;
對於cpu的限制,mesos有兩種方式:
- cpu shared方式:這種方式對 cpu 沒有嚴格限制,機器上的任何task均可以訪問機器上全部cpu資源,好比你限定的cpu使用資源是2, 這種方式可能使用到4,6或更高;
- cpu CFS方式: 至關於配置了獨佔 cpu, 好比cpu配置爲1,那麼這個任務的 cpu 使用率就不會超過 100%, 至關於設定了一個hard limit;
在咱們的大部分環境中,受限於kernel版本,mount namespace不支持,所以咱們採用rootfs + chroot的方式來做簡單的資源隔離;
咱們定製了若干版本的rootfs, 任務打包就是將任務自己的依賴和相應rootfs結合的過程, 打包好能夠放到s3等存儲上,供marathon部署任務時調用。
這裏咱們結合marathon的一個任務部署的json配置來說一下, 先看一個這個配置, 我將說明直接寫在裏面
關於chroot, 你們能夠參考下面的網址內容,簡單講就是構造了一個沙箱,和已有的文件系統隔離;
https://www.ibm.com/developerworks/cn/linux/l-cn-chroot/
機器自己的基礎監控通常公司還有本身的統一監控, 這部分不用投入精力;
咱們主要關注task的調度運行狀況,目前的方案是mesos-exporter和mesos-agent(或mesos-master)一塊兒部署,上報監控信息到prometheus,使用grafana來展現;
mesos自己爲咱們提供了很豐富的http api來獲取當前集羣的屬性,狀態,Framework狀況,task的運行狀態等等,結合這些咱們本身來做監控其實也不是難事,能夠參考這裏:
http://mesos.apache.org/documentation/latest/operator-http-api
打包task沒有實現自動化, 咱們雖然定製了若干種不一樣的rootfs, 好比c++11環境的, python環境的, java環境的等等, 可是想要運行的task依賴千差萬別, 如今都是結合rootfs和業務的程序,手動合成專用的rootfs, 基本上每一個task都要走這個手動流程,煩鎖,耗時,容易出錯;
目前只引用了marathon一種調度框架,適用於長期運行的task, 對於須要定時運行的task目前沒法支持;
到此咱們利用Mesos構建的多任務調度系統就簡單介紹完成,其中還有不少不完善的地方,有興趣的同窗能夠一塊兒討論,互相學習~~~