數人云上海&深圳兩地「容器之 Mesos/K8S/Swarm 三國演義」的嘉賓精彩實錄第四彈!小數已經被接連不斷的乾貨搞暈了,沉浸技術的海洋好幸福~Windows container 在國內的實踐還比較少,攜程做爲.Net 大戶,率先進行了調研和實踐應用,將其中的成果與你們分享。java
羅勇,攜程雲平臺開發經理
主要負責攜程雲平臺建設和維護,熟悉 OpenStack , Docker , Linux/Windows Container 等技術領域python
今天的主題是 Windows 容器。今年下半年攜程開始了對 Windows container 的調研工做,目前已經有一些成果和實際應用案例,與你們分享一下,主要內容有:linux
攜程爲何要使用 Windows container
(可能國內大部分的人瞭解 Windows container 少一些,特別是具體的實踐,分享重點會偏 Windows container 細節)web
傳統.Net 應用容器化實踐shell
容器存儲&網絡&編排安全
攜程是.Net 應用大戶,由技術棧決定的,早期攜程整個應用架構都放在該平臺上,線上跑了 3000 多個核心應用,覆蓋了 20 多個 BU (業務部門),這讓咱們不得不關注這一龐大的系統。服務器
平臺要往 java 方面轉,去分享 java 的紅利,可是.Net 線上應用不可能都重寫;網絡
.Net 的應用目前 90%左右的應用都跑在虛擬機上,從虛擬機自身來看,粒度太粗,對資源的使用率還不是很好。架構
持續發佈,應用上線,從拿到機器環境準備好環境上線生產,虛擬機模式下週期長,擴容慢。工具
新一代發佈平臺的需求,但願縮短環境準備時間,作到秒級部署, Linux 平臺的應用很是容易作到,可是 Windows .Net 應用在這方面支持比較難,另外,爲了確保生產和測試環境高度一致,但願應用發佈是單一應用、單一鏡像的,最好是一個容器儘可能少的包含系統進程,這樣能夠把資源隔離的粒度控制在小範圍內,儘可能榨取宿主機的資源,同時但願 Linux 容器和 Windows 容器的方案儘量接近,好比網絡、存儲,不須要兩套不同的方案或是有大的有變化。
最開始的時候攜程用物理機部署應用,爲了保證互不衝突,用戶在一個物理機上只部署一個應用。後來認爲此舉太浪費,就部署了多個應用,可是爲管理帶來了麻煩,應用之間有必定的衝突或者相互影響。以後有了虛擬機,虛擬機上能夠部署更多的應用,並且隔離比較好,不過虛擬機資源隔離的粒度太粗了,因而容器走了過來,能作到把一個應用打到包裏,這個包涵蓋了環境配置等, run 起來能夠只是一個進程,又具有必定的隔離性,同時把資源使用的粒度控制足夠的細。
Windows container 目前支持的系統是 Windows server 2016 ,這個版本是去年 10 月份正式發佈的(攜程是國內比較早的一批拿到了他們的 RTM 版本),支持兩類 server ,一類是 server core ,另外一類是 nano server 。 nano server 是微軟比較推薦的一類服務器系統,啓動很是快,能夠大幅度縮短計劃內維護宕機時間,一般幾秒鐘就起來了,不包含硬件檢測的時間,幾十秒都可以起來。這塊攜程尚未用於生產環境,目前只測試了用 server core 做爲容器宿主機的系統的狀況。須要着重提一下的是,若是宿主機打了補丁或者升級,容器也要對應的作補丁或者升級。固然不必定說立馬作補丁升級,但必定要比較精確的找到對應的版本作升級。
Windows container 有兩種 container 類型,這兩種容器都是跑到 Windows servrer 2016 的,但還有一種容器的玩法是在 Liunx 平臺跑.Net core ,這種方案咱們也看過,你們很容易想到它的侷限,其實只能跑到用.Net 技術開發的 Windows 的應用,一些非.Net 的應用不支持,所以這個方案被 Pass 了。直接在 Windows server 跑容器的方案更爲靠譜,該方案有兩種類型, Windows server 和 hyper - v container 。
有人會問, hyper-v 不就是一個虛擬機的技術嗎?對,其實它有點像虛擬機,可是 hyper - v 的技術略有不一樣,速度會明顯比虛擬機快不少,只是在申請資源或者獲取資源時,比 Windows server Container 的速度稍稍慢一點點, Windows server container 可能 3 秒,它可能 4 、 5 秒。可是資源的隔離度比較好一些,相似於虛擬機,微軟公有云 Azure 的容器服務也是採起這種容器類型,他們的考慮是公有云上面部署的應用不是受信任的,相互之間有可能「打架」的狀況發生,他想隔離好一些。
另外一個區別, Windows server Container 的內核是共享的,能夠在宿主機上看到每一個容器裏面的進程,這與 Linux 容器類似,能夠直接 kill 掉。 hyper-v container 宿主機是看不見容器內進程的,像一個虛擬機同樣。此外,內存資源隔離不一樣, Windows server Container 內存能夠 share , hyper-v container 不能 share , hyper-v container 一旦分配就不能從新進行修改。對系統應用是信任的,這種比較適合作私有云的一些產品,由於在應用上跑的什麼東西,這個應用能幹什麼壞事或者是相互之間有沒有影響,均可以控制,可是公有云不能這樣作,應用使用率很高,會把別的容器影響到。啓動速度上也會有差異,一個啓動快,一個啓動慢一點,固然並非特別慢。
容器鏡像,這個和 Linux 容器的鏡像相似,能夠分層。最下面一層是基礎鏡像,可是基礎鏡像和 Linux 有區別。 Linux 鏡像能夠本身搞,弄一個系統把它作成鏡像,可是微軟沒有辦法本身作一個 Windows container base 鏡像。或者說如今只是 Windows server 2016 的鏡像,想跑一個 2012 的系統是不行的。當前系統內核只能支持 win10 ,在上面能夠繼續安裝想要的東西,好比接着安裝 Framework ,而後在最上面裝應用。
鏡像構建也是同樣, Windows container 容器和 Docker 集成比較好,能夠用 Docker 工具的一些命令進行 build ,用 Dockerfile 來 Build 一個鏡像。 registry 是鏡像能夠直接 push 到一個平臺或者是私有的 registry 上面去,經過 Docker pull 方式拉下來, Docker run 跑起來。
Windows container 的鏡像,能夠在 Docker 網站上能夠找到關於 Windows container 的一些 base image, pull 下來大概有 8G 左右,在外網上下載可能要兩天。你們能夠嘗試一下。也能夠建私有的 registry ,攜程採用的 VMware 開源的 Harbor 方案,自己沒有作太多的修改,直接能夠用。和攜程的 AD 整合之後基本上能用了, registry 能夠把 Linux 和 Windows 的鏡像都放在一塊兒,兩邊都能用,都能管,這部分省掉了不少的內容,不須要作額外的開發,這樣 Windows 和 Linux 的平臺的 image 管理方案是一致的。
以前提到攜程有 3000 多個.Net 應用,這些應用天天要不停的發佈、測試、編譯打包,是一項很大的繁瑣工程,有個叫「 build 」的項目負責這個事情。最初這些跑在虛擬機裏,資源使用率很低,白天很忙,晚上使用率很低,有必定的資源浪費,且構建環境也常常不一致。爲了積攢容器應用使用的經驗,咱們考慮把 build 項目先容器化,也就意味着.Net 應用本身的編譯在容器裏面編譯,看能撞出來什麼樣的火花。
原來寫幾千個應用的編譯腳本,若是改了一些東西,變動維護的代價是很是大的,儘可能這個方案不要用到原來以往用的工具和使用方式,不去動它,最好可以拿過來不怎麼修改,就跑起來。另外,重點看一下像 vs2010 和 vs201 這樣的工具能不能在容器裏跑,實踐證實是能夠的。而後看 MSBuild 在容器裏面是否兼容,支持不一樣的.Net Framework 版本,這些都是比較通用的軟件,結果是這些功能都可以支持,另外也包括 python 、 MVC 、 GIT 等等。
首先環境,編譯的環境高度一致,每一個環境沒有太多的區別,容器拉起來直接跑,提升了編譯成功率。
其次資源利用率提升了,咱們把虛擬機資源砍掉了一半,就只須要兩臺宿機機搞定整個攜程 3000 多個.Net 應用的編譯。
編譯時長也縮短了,原來用一次構建平均要幾分鐘,如今 90 秒左右基本上能構建完成。
圖形不支持,這個是某些企業想用 Windows container 的大問題,它自己圖形不支持。後臺程序沒有太大問題,不過有一些依賴圖像工具比較難支持。
舊應用兼容不是很好。好比遇到 MGwin 編譯出來的包,一旦代碼中有調用標準輸出的語句程序直接就掛了,遇到這類問題,須要把源碼拉下來從新編譯,比較有難度。
不支持 RDP ,遠程桌面是不能用的,那怎麼作到遠程訪問呢? 還好 Windows 如今支持 SSHD 安裝了,只須要容器內裝一個 SSHD ,而後遠程 SSH 去,固然能夠用 powershell 遠程的登陸方式,兩種方案均可以用, SSH 方案更統一一些, 若是用戶當前正在 Linux 平臺上工做,忽然想登一個 Windows 的容器怎麼辦?固然也能夠用 linux 平臺的 powershell 工具實現遠程登錄容器。
不支持 D 盤。攜程遷移過來不少老的應用是要裝在 D 盤的,容器拉起來沒有 D 盤,只有一個 C 盤。自己 Docker 有一個 volume 功能,能夠掛一個數據的盤,問題是這樣會致使在宿主機上留下一些東西,和宿主機產生耦合,若是容器刪除或者遷移,宿主機上就留下了髒數據。後來咱們爲 D 盤作一個 link ,至關於 D 盤能夠快捷的方式連到 C 盤,映射到 C 盤的某個目錄,這樣數據都是落地到在容器的磁盤上,若是想在別的地方拉起來這個容器,能夠直接 push register ,就能夠在別的地方部署且環境同樣。
接下來 Windows container 容器的存儲,網絡,編排方面的技術與你們分享一下。
Windows container 資源的隔離方式和配置管理 API 是借用 Docker 規範,設計理念和 Linux Container 相似,也支持 CPU share 的這種方式去控制資源的分配。內存能夠經過 quota 的方式去分配內存, Disk 也可以充分應用到 IO 的帶寬,這一塊尚未作很是多嚴格的測試。關於網絡的支持,攜程作了不少測試,總體來說比較不錯,問題較少。性能也知足需求,多個容器在一個同一個宿主機上也能儘可能用到整個宿主機的帶寬。
存儲有三種:一種是鏡像,鏡像自己是一個存儲,設計之初定義就不是一個永久的存儲,當前容器存儲拉掉那個存儲就沒有了,也不是設計安全的。另一種存儲是 volume (卷) ,能夠掛一個數據盤到某一個容器上,在容器裏擴展存儲空間。同時多個容器也能夠掛載宿主機上的一個同一個 volume (卷目錄),這樣你們能夠實現 NFS 同樣的效果。最後一類存儲是網絡存儲,好比能夠用 SMB 的方式掛網絡盤在容器裏面使用,裏面若是有萬兆的帶寬支持還能夠玩一下,若是沒有萬兆帶寬的話就不要玩了,它只能放一些冷數據。
相對來說複雜一些, Windows 支持有四種網絡模型,第一種 NAT 模式你們比較熟悉,起一個本地或者是數據本地的 IP 地址,若是你想外網訪問的話,把 Docker 映射出來,這種方式比較適合作一個 JOB 類型的應用在上面,不須要外邊能夠訪問它,可是容器裏面能夠去下載東西。以前講的 build 項目就是用這個網絡模型,很是簡單,不須要考慮太多網絡的模型就能夠直接用。
第二種是 transparent 網絡模型,這種模型是如今主要用於生產的模型,首先它是經過 mac 地址假裝實現數據透傳,對網絡的性能自己折損也比較少,它也支持把多個工做網卡綁到一個交換機上,而後把這個交換機給容器用。網絡模型在容器宿主機之外的機器上看到 Windows 容器和一臺物理機沒有什麼區別。
還有一種是 L2 bridge 這種採用 openstack 網絡的 Flat 模式,所用的網絡跟宿主機的網絡是同樣的,和宿主機在同一個網段,這樣有很大的侷限性,網絡和宿主機混在一塊兒沒有辦法作到多租戶隔離,而後網段用光了就完了,適用於比較小的集羣。
最後一種是 Tunnel mode ,沒有太多研究這一種,可是微軟 Azure 用的這一種網絡模型。自己攜程爲了和虛擬機的不少的品牌網絡模型一致,因此這一種沒有那麼快的推動。
Hyper-v 宿主機是 2012 上面 hyper-v 的網絡模型,以前要求一臺宿主機儘可能要 4 塊網卡,爲何要用 4 塊網卡?兩塊給虛擬機用,另外兩塊作一些管理,好比對存儲用,虛擬機遷移等,能夠作宿主機的管理。另外一種方式, 2016 建議的一種網絡方式,這裏面有一個叫作 embed team ,內嵌交換機,它的好處是把下面不管是兩塊仍是 N 塊網卡均可以綁在一個 bound ,而後把這個 bound 放在一個交換機裏面,每一個容器 port 所有放在交換機裏面,而後容器給 port 打相應的 vlan tag ,這樣容器的網就通了。
embed team 的好處是不須要要求宿主機必定要有這麼多的網卡才能夠用,另外一個好處是對這些不一樣的 vlan 之間作一些流量的控制,攜程的 container 的網絡模型也是基於嵌入式交換機上實現的。把宿主機至少兩塊網卡作了 bound ,放在一個 embed team 裏面去,另外加一個 port 給宿主機作管理網卡。容器宿主機相比虛擬機宿主機簡單,沒有存儲和遷移的需求,就不要以額外的劃分網絡了,若是須要爲容器的存儲單獨掛一個網絡的話能夠加一個 Port 作這個事情。不一樣的網段的這種容器在上面能夠再建立不一樣的 Docker ,加不一樣的 port ,而後容器在裏面能夠互通,這樣的好處就是既實現了多租戶、實現了網絡隔離,同時和虛擬機包括 Linux 上面的網絡模型是一致的。
編排這塊一般一個容器部署到多個宿主機上,同時一套應用下來有數據層、業務層、也有 web 層,這些應用要分開放,它們中間放在哪裏須要有一個地方,把整個管起來,也但願這個東西能自動化,自己作編排這些,不管是 Swarm 、 K8S 、 Mesos 都是須要解決的問題。一種方案是用 Docker compose 這種方式,適合於單宿主機管理。想編排一下容器,看如何跑,這種方式用 Docker compose 就能解決。固然,微軟如今對 Docker Swarm 支持好一些,實現成本比較低,基本上能管,可是性能方面沒有作太多的測試,目前一些基本的調度、主機分類等等都能用。
由於攜程的 Linux 平臺用的也是這套方案作的編排相關的管理,但願有一套方案可以儘可能兩種容器一致,因而咱們的方案採用 Mesos 加上 Marathon 對它進行管理,自己它也有一些現成的工具,好比 UI 等現成的工具均可以用,這部分還在進行測試和研究中。官方下來的包不能直接跑到 Windows server 上面,要拿下來從新編譯才能用。最終攜程是想作到這麼簡單的一個容器的管理的架構,就是說但願 Mesos 在裏面可以同時管 Linux 容器和 Windows 容器,對它進行統一的調度,最大限度的優化這種調度策略,提高使用率,這是最終總體的設計理念。
有一些急迫解決的問題,與你們交流一下。首先 Windows container 的鏡像比較大,在生產環境,若是批量 pull base image ,網絡的帶寬會很快被打滿,會對業務帶寬形成影響。咱們須要有一套方案來解決這個問題, 如何可以比較「經濟」的方式把 Based image 或者變動的 Layer 文件下發下去,是後續要解決的問題。
Windows container 的監控日誌,沒有現成的方案,我也有與微軟團隊交流過,這部分文檔很是少,攜程以後也會重點解決監控問題。
推行單容器、單應用的發佈方式,但願後面可以把各類 FAT/UAT/Prod 環境之間打通,均可以經過 Windows 容器方式,秒級發佈。
攜程有 3000 多個應用,一旦容器跑起來了,宿主機的規模仍是比較可觀的,這種狀況下,大規模容器如何管理好?這也是後面須要解決的問題。
這是我今天給你們分享的主要的內容,謝謝你們!