趙培龍
(同濟大學電子與信息工程學院,上海201804)
ContainerSSh:基于WebSocket的Linux容器遠程訪問解決方案
趙培龍
(同濟大學電子與信息工程學院,上海201804)
云計算[1]是一種新的商業模式,它可以通過動態的,可擴展的方式來使用資源,使得資源充分利用,滿足不同類型的應用。其中平臺即服務(PaaS)[2]處于基礎設施即服務(IaaS)與軟件即服務(SaaS)之間,PaaS實際上是由一系列通用的功能抽離出來的開放API和SDK,使得底層對用戶保持透明,可以讓用戶專注于業務開發,降低用戶開發成本。
目前國內外已經有多個PaaS產品,國內有新浪SAE、百度BAE,國外有Google的GAE、微軟Azure Service、亞馬遜Web Services。雖然PaaS眾多,但是對比于IaaS,PaaS并沒有很流行,原因在于這些大大小小的PaaS平臺為了對其自身系統進行保護,一般都會對用戶的應用進行一些額外的限制,例如不能使用本地磁盤寫、應用服務無狀態等,這些要求就形成了其PaaS自身獨有的開發標準,用戶必須遵守其標準進行開發應用,一般各個PaaS平臺的標準是不一樣的。再者,一個PaaS平臺并不一定能完全滿足用戶所有的需求,用戶想要增加自己的新服務要么等PaaS提供商開發,要么只有用自己的服務器,從這點來說PaaS并沒有完全解決所有用戶的痛點。而IaaS提供彈性虛擬機的方式最大限度的為用戶提供了基礎設施,用戶的應用沒有平臺的約束,其應用可以很方便的遷移到云端。同時,PaaS一般為了實現高可用以及運行效率,一般都是采用的多租戶模式,這種方式一般都會導致比IaaS更加麻煩的安全隔離問題[3]。
近年來以Docker為代表的容器引擎大大的改造了傳統的PaaS服務,Docker使用操作系統虛擬化,層疊式文件系統以及統一的配置標準的一系列技術都為PaaS提供了較好的資源隔離以及規范了用戶應用的打包部署流程,不僅僅在一定程度上解決了多租戶隔離以及平臺遷移的問題,也解決了用戶在PaaS中增加用戶自定義服務的問題。使用容器的PaaS平臺的代表有Google的GCE、阿里的ACE。
Docker一般可以通過DockerFile的方式來配置用戶自定義的服務,但是這種方式學習曲線太高,對用戶不友好,第二種方式則是在容器啟動之后再啟動一個sshd服務,用戶通過ssh直接訪問容器進行控制,這種方式的優勢就是不需要用戶進行新的學習,直接上手,但是其缺點則是需要在容器中開額外的進程服務,會浪費一定的系統資源,再者PaaS中一般不會給一個容器分配固定IP,所以通過這種方式訪問則需要進行ssh的代理,這種四層代理會增加網絡的復雜性,也不利于容器的訪問控制。
綜上,本文設計的ContainerSSh系統,這是一款專門針對PaaS中的容器訪問而提出來的,基于瀏覽器訪問控制容器的Web終端模擬器系統,用戶只需要在瀏覽器上輸入相關uri就可以方便的訪問和控制用戶在PaaS中的容器,其優勢在于無需特別的客戶端,只需要瀏覽器,而且基于七層代理[4],能對流量和訪問進行更加進行精準的控制,保證容器安全。

ContainerSSh的整體設計如圖1所示,整個系統包含有5個獨立的子系統:用戶終端程序、統一代理服務器、驗證服務器、Docker守護進程、Docker容器。

圖1 ContainerSSh系統部署圖
五個子系統之間都通過RESTful API[5]進行通信,用戶終端是運行在用戶的瀏覽器上,其給用戶呈現一個Linux終端仿真器,與Linux自身終端體驗效果一致。用戶訪問容器的所有流量首先都會通過橋接服務器,它會把不同的用戶的流量指配到若干臺機器中,用戶流量被制定到某臺機器后,Browser Agent會將用戶的流量直接輸入到Docker守護進程中從而達到與Docker容器交互的目的,其中Browser Agent和Docker守護進程需要部署在同一臺機器上。

ContainerSSh整體架構如圖2,大致可分為3層,視圖層、管道層、服務層外加一個監控服務 。
視圖層主要是運行在用戶瀏覽器上的Web模擬終端。
管道層是用戶瀏覽器與后端服務交互的管道類型,其主要目的是維護前后端的通信任務,根據通信的目標不一樣所以劃分了有三種不同的管道,WebSocket,RESTful API,Static file server。WebSocket Channel是負責將用戶在模擬終端中的輸入數據以及容器中的輸出數據打通,這是操縱容器的數據流通道,RESTful API channel是對外開放的API,主要目的是提供ContainerSSh系統的運行狀態信息,以便系統管理員能熟知系統整體運行狀況,Static file Server是一個內置的Web服務器,其作用主要是提供前端的靜態文件。
服務層主要通過WebSocket Channel以及RESTful API的方式與前端通信,Proxy Services是作為整個服務系統的接口,所有的流量都將從這里進出,它負責容器的分配以及channel的控制。Monitor監控整個服務層的健康狀況,例如機器過載,惡意調用API等,它會向Proxy Service發出相關命令執行相關任務,例如斷開鏈接,拒絕某個用戶請求等。Container Service主要是容器相關的操作,這部分的工作大部分是依賴于Docker這個開源的工具,Proxy Service會直調用其API來控制容器。


圖2 ContainerSSh系統架構圖
在瀏覽器上的服務基本上都是基于HTTP協議進行通信,但是HTTP協議是基于請求-相應的模式設計的,且是單向無狀態協議[6],直接使用其并不能滿足基于瀏覽器的終端的實時性的要求。
業界對于Web實時通信一般使用AJAX輪詢方式,通過客戶端頻繁與服務器建立連接查詢的方式實現實時通信,但由于TCP連接一次建立也需要消耗相當的資源,所以一般這種方式效率太低,并不能有效地實現實時通信[7]。為了解決這個問題,IETF(互聯網工程任務組)以及W3C一起制定了WebSocket協議[8],W3C制定了WebSocket API,IETF基于HTTP實現了Web-Socket。WebSocket協議改變了HTTP的請求-相應模式,能夠真正建立起服務端與客戶端的全雙工通道。基于WebSocket就能夠實現ContainerSSh的實時通信,能夠顯著地減少雙向數據的時延以及系統的負載。

ContainerSSh通過uri辨別的方式來把不同用戶的請求定位到不同的容器里中,所以ContainerSSh需要實現代理服務,將不同的用戶流量導入到對應的容器中。
(1)連續中繼代理
在實現代理服務的時候考慮到系統的健壯性,在Browser Agent的前端增加了一個橋接服務器,其目的是對Docker服務器集群進行負載均衡以及安全檢查,防止惡意用戶攻擊系統以及單點故障。
所以ContainerSSh從用戶到最終容器的數據流要經過以下幾個步驟:
①客戶端調用橋接服務器的API,要求與指定容器進行通信。
②橋接服務器收到調用請求之后會對其進行用戶校驗,若校驗成功則返回客戶端靜態文件,若是失敗則返回相關的錯誤信息。
③若橋接服務器允許調用,那么瀏覽器會得到正確的客戶端代碼,接受完客戶端代碼之后客戶端的代碼會自動執行,主動向橋接服務器發起websocket連接。
④為了防止用戶惡意頻繁調用系統,導致系統資源緊張,所以制定了一個用戶同一時間內只能使用一個容器鏡像實例的規則,所以橋接服務器接受到該websocket連接之后,會首先根據用戶以及請求的容器鏡像信息進行異常檢測,防止出現惡意調用的情況。若是出現異常則直接返回錯誤代碼給客戶端。
⑤通過異常檢查之后,橋接服務器將會從Docker服務器集群選出一臺服務器來處理該次請求。
⑥橋接服務器會先對選出的Docker服務器的Browser Agent發起websocket連接,Browser Agent收到連接之后,直接調用Docker daemon的API創建及運行容器,其也是使用websocket與Docker daemon進行通信。最終用戶在客戶端上的輸入數據,就用橋接服務器轉發到Browser Agent然后轉發到Docker daemon,最后進入到容器當中;容器中的輸出數據首先流入到Docker daemon,然后轉發到Browser Agent,然后又到橋接服務器,最后到達用戶終端。
(2)中斷處理
由于整個系統中數據被代理轉發的次數較多,所以如果有一處連接斷開,那么整個數據鏈路就會出現斷裂,如果系統不能夠及時的檢測到斷裂并且清理掉數據鏈路,那么用戶終端會出現假死的情況,所以當出現某處連接斷開時,系統應該能夠自動自動檢測出并關閉整個數據鏈路,提示用戶出錯信息。基于此需求,ContainerSSh實現了一種保險融斷機制:當輸入輸出流中有一方突然關閉,那么會自動關閉另外一方。系統中所有代理處都是使用了這樣的機制,所以當出現某處I/O斷開的時候,系統能夠沿著數據鏈路依次關閉,最終通知到最終端。
偽代碼如下:

Source代表輸入流,dest代表輸出流,只要任意一方流關閉,則會關閉另外一方流,且執行錯誤處理函數。
本節主要測試ContainerSSh的主要功能,包括訪問控制容器測試,API頻繁調用檢查測試,連接中斷測試。

使用ContainerSSh與傳統SSh同時登錄容器,在ContainerSSh或SSh中輸入指令,觀察另外一方是否同步。
效果如圖3,無論從ContainerSSh還是傳統的SSh發送指令,另一方都可以即時收到數據。

圖3 ContainerSSh連通測試

首先在一個瀏覽器中訪問如下uri來登陸一個容器:

容器登錄成功之后,再次調用該uri,效果如圖4,系統成功阻止了API相同時間多次調用的問題。

圖4 API調用檢查測試

同樣使用ContainerSSh與傳統SSh同時登錄容器。
先關閉ContainerSSh的容器中斷,觀察傳統SSh是否被關閉,效果如圖5(a)。
再同時使用ContainerSSh與SSh登陸容器,使用Docker kill命令直接關閉容器,瀏覽器上的終端也同時關閉了,效果如圖5(b)。
隨著容器技術在云計算當中越來越廣泛的應用,各類基于容器技術的云平臺也是越來越多,由于大多數云平臺的限制,其一般不會為容器分配固定IP,所以當用戶有直接訪問容器的需求時,如何讓用戶能夠方便的訪問平臺中的容器以及如何在多租戶的情況下保障平臺安全的問題成為了基于容器的云平臺所需要解決的問題。
ContainerSSh利用 websocket技術以及容器引擎Docker構建了基于Docker云平臺的容器訪問解決方案,能夠有效地解決用戶直接訪問容器的問題并且也能夠對系統提供一定的安全保障。

圖5
[1]吳吉義,平玲娣,潘雪增,等.云計算:從概念到平臺[J].電信科學,2010(01):1-11.
[2]Kibe S,Watanabe S,Kunishima K,et al.PaaS on IaaS[C].2013 IEEE 27th International Conference on Advanced Information Networking and Applications(AINA).IEEE Computer Society,2013:362-367.
[3]林兆驥,付雄,王汝傳,等.云計算安全關鍵問題研究[J].信息化研究,2011(02):1-4.
[4]黎哲,郭成城,陳亮.一個基于TCP遷移機制的第七層負載均衡系統[J].計算機應用研究,2005(04):116-118.
[5]Taylor R N,California U O,Irvine.Principled Design of the Modern Web Architecture[C].Software Engineering,2000.Proceedings of the 2000 International Conference on.IEEE,2000:407-416.
[6]吳曉東,王鵬.Html5的通信機制及效率的研究[J].長春理工大學學報:自然科學版,2011(04):159-163.
[7]Pimentel V,Nickerson B G.Communicating and Displaying Real-Time Data with WebSocket[J].IEEE Internet Computing,2012,16 (4):45-53.
[8]W3C.The WebSocket API[EB/OL].http://www.w3.org/TR/2012/CR-websockets-20120920/2015.10.28.
Docker;Container;PaaS;Cloud Computing;WebSocket
ContainerSSh:Linux Container Remote Access Solution Based on WebSocket Protocol
ZHAO Pei-long
(School of Electronics and Information Engineering,Tongji University,Shanghai 201803)
1007-1423(2015)36-0071-05
10.3969/j.issn.1007-1423.2015.36.016
趙培龍(1990-),男,四川綿陽人,碩士研究生,研究方向為容器與云計算
2015-11-10
2015-11-30
隨著容器技術在云計算中的大量應用,以Docker為代表的容器引擎在PaaS中大放光彩,出現一大批基于Docker的云計算初創公司。然而由于基于容器的云平臺的特殊性,一般不會為容器分配固定IP,導致用戶無法直接對云平臺中的容器進行訪問控制,對用戶添加自定義服務等操作增加不便,ContainerSSh則是專門針對該問題而設計的解決方案。
Docker;Container;PaaS;云計算;WebSocket
With the development of container technology in cloud computing,it has been a large number of applications are created in cloud computing,Docker is a popular container engine and a lot of startups provide services based on Docker.So container technology has a very important for PaaS.However,due to the special nature of cloud platform based container,most of cloud platform will not assign fixed IP to container,user can not directly access and control the container in the cloud platform,so users are difficult to add personalized service. ContainerSSh is a solution that is designed to solve that problems.