總結多種容器化技術對比

總結多種容器化技術對比

1、chroot和jails

在容器化技術方面,其實歷史很久遠了。雖然我們現在用的容器化技術,或者說 k8s,還有云原生的概念是近幾年才火起來的,但是實際上就容器化技術的發展來說,其實是很早的了。比如說最早的時候來自chroot,chroot大家可能都用過,或者都有了解過,在1979年的時候它是來自Unix,它主要的功能是可以修改進程和子進程的/。

通過使用chroot達到什麼樣效果呢?使用chroot加某一個目錄,然後再啓動一個進程,那麼這個進程自己所看到的 / ,就是我們平時所說的 / 目錄,這個 / 就會是我們剛纔指定的文件夾,或者說剛纔指定的路徑。這樣子的話可以有效的保護我們操作系統上面的一些文件,或者說權限和安全相關的東西。

在2000年的時候,出現了一個新的技術,叫做jails,其實它已經具備了sandbox,就是沙箱環境的雛形。使用jails的話,可以讓一個進程或者說創建的環境擁有獨立的網絡接口和IP地址,而當我們提到使用jails的話,我們肯定會想到一個問題,就是如果你有了獨立的網絡接口和IP地址,這樣的話就不能發原始的套接字,通常跟原始的套接字接觸得比較多的就是我們使用的Ping命令。默認的情況下,這樣子是不允許使用原始的套接字的,而有自己的網絡接口和IP地址,這個感覺上就像是我們常用的虛擬機。

圖片

2、Linux VServer和OpenVZ

接下來在2001年的時候,在Linux社區當中就出現了一個新的技術叫做Linux VServer。Linux VServer有時候可以簡寫成lvs,但是和我們平時用到的4層的代理lvs其實是不一樣的。它其實是對Linux內核的一種Patch,它是需要修改Linux內核,修改完成之後,我們可以讓它支持系統級的虛擬化,同時使用Linux VServer的話,它可以共享系統調用,它是沒有仿真開銷的,也就是說我們常用的一些系統調用、系統調用的一些函數都是可以共享的。

在2005年的時候,出現的一個新的技術—OpenVZ。OpenVZ其實和Linux VServer有很大的相似點,它也是對內核的一種Patch,這兩種技術最大的變化就是它對Linux打了很多的Patch,加了很多新的功能,但是在2005年的時候,沒有把這些全部都合併到Linux的主幹當中,而且在使用OpenVZ的時候,它可以允許每個進程可以有自己的/proc或者說自己的/sys。

其實我們大家都知道在Linux當中,比如說啓動一個進程,你在他的/proc/self下面,你就可以看到進程相關的信息。如果你有了自己獨立的/proc,其實你就可以達到和其他的進程隔離開的效果。

接下來另外一個顯著的特點就是它有獨立的users和groups,也就是說你可以有獨立的用戶或者獨立的組,而且這個是可以和系統當中其他的用戶或者組獨立開的。

其次的話OpenVZ是有商業使用的,就是有很多國外的主機和各種VPS都是用OpenVZ這種技術方案。

圖片

3、namespace 和 cgroups

到了2002年的時候,新的技術是namespace。在Linux當中我們有了新的技術叫做namespace,namespace可以達到進程組內的特定資源的隔離。因爲我們平時用到的namespace其實有很多種,比如說有PID、net等,而且如果你不在相同的namespace下面的話,是看不到其他進程特定的資源的。

到了2013年的時候,產生了一個新的namespace的特性,就是user namespace。其實當有了user namespace,就和上文提到的OpenVZ實現的獨立用戶和組的功能是比較像的。

對於namespace的操作當中,通常會有三種。

1)Clone

可以指定子進程在什麼namespace下面。

2)Unshare

它是與其他進程不共享的,unshare再加一個-net,就可以與其他的進程獨立開,不共享自己的net,不共享自己的網絡的namespace。

3)Setns

就是爲進程設置 namespace。

到了2008年,cgroups開始被引入到Linux內核當中,它可以用於隔離進程組的資源使用,比如說可以隔離CPU、內存、磁盤,還有網絡,尤其是他在2013年和user namespace進行了一次組合之後,並且進行了重新的設計,這個時候,就變得更現代化了,就像我們現在經常使用到的Docker的相關特性,其實都來自於這個時候。所以說cgroups和namespace構成現代容器技術的基礎。

圖片

4、LXC 和 CloudFoundry

在2008年的時候,新的一項技術叫做LXC, 我們也會叫他Linux Container(以下均簡稱LXC)。上文我們提到了很多容器化的技術,比如Linux VServer、OpenVZ,但是這些都是通過打Patch來實現的,而LXC是首個可以直接和上游的Linux內核共同工作的。

LXC是可以支持特權容器的,意思就是說可以在機器上面去做uid map、gid map,去做映射,而且不需要都拿root用戶去啓動,這樣子就具備了很大的便利性。而且這種方式可以讓你的被攻擊面大大縮小。LXC支持的這幾種比較常規的操作,就是LXC-start,可以用來啓動container,LXC-attach就可以進入container當中。

到2011年的時候,CloudFoundry開始出現了,他實際上是使用了LXC和 Warden這兩項技術的組合,在這個時候不得不提到的,就是他的技術架構是CS的模式,也就是說還有一個客戶端和server端,而 Warden容器,它通常是有兩層,一層是隻讀os的,就是隻讀的操作系統的文件系統,另外一層是用於應用程序和其依賴的非持久化的讀寫層,就是這兩層的組合。

我們之前提到的技術,大多數都是針對於某一臺機器的,就是對於單機的。CloudFoundry它最大的不同就是它可以管理跨計算機的容器集羣,這其實就已經有了現代容器技術的相關特性了。

圖片

5、LMCTFY和systemd-nspawn

在2013年的時候, Google開源了自己的容器化的解決方案,叫做LMCTFY。這個方案是可以支持CPU、內存還有設備的隔離。而且它是支持子容器的,可以讓應用程序去感知到自己當前是處在容器當中的。另外還可以再爲自己創建一個子容器,但是隨着2013年發展之後,它逐漸發現只依靠自己不停的做這些技術,就相當於單打獨鬥,發展始終是有限的,所以它逐步的將自己的主要精力放在抽象和移植上,把自己的核心特性都移植到了libcontainer。而libcontainer之後就是Docker的運行時的一個核心,再之後就是被Docker捐到了OCI,再然後就發展到了runC。這部分內容我們稍後再詳細講解。

大家都知道服務器它肯定是有一個 PID爲1的進程。就是它的初始進程、守護進程,而現代的操作系統的話,大多數大家都使用的是systemd,同樣systemd它也提供了一種容器化的解決方案,叫做 systemd-nspawn。這個技術的話,它是可以和systemd相關的工具鏈進行結合的。

systemd除了有我們平時用到的systemctl之類的,還有systemd machine ctl,它可以去管理機器,這個機器支持兩種主要的接口,一種是管理容器相關的接口,另外一種是管理虛擬機相關的接口。

而我們通常來講,就是說systemd提供的容器技術解決方案,它是允許我們通過machine ctl去容器去進行交互的,比如說你可以通過machine ctl start,去啓動一個systemd支持的容器,或者通過 machine ctl stop,去關掉它,而在這種技術下,它是支持資源還有網絡等隔離的,其實它最主要的是systemd ns,它其實是使用namespace去做隔離。對於資源方面是來自於systemd,systemd是可以使用cgroups去做資源隔離的,其實這也是這兩種兩種技術方案的組合。

圖片

6、Docker

而在2013年Docker也出現了。通常來講,Docker是容器時代的引領者,爲什麼這麼說呢?因爲Docker在2013年出現的時候,他首先提到了標準化的部署單元,就是Docker image。同時它還推出了DockerHub,就是中央鏡像倉庫。允許所有人通過DockerHub去下載預先已經構建好的Docker image,並且通過一行Docker run就可以啓動這個容器。

在衆多使用起來比較繁瑣、比較複雜的技術下,Docker這時提出來,你只需要一行Docker run,就可以啓動一個容器,它大大簡化了大家啓動容器的複雜度,提升了便捷性。

所以Docker這項技術就開始風靡全球。而Docker它主要提供的一些功能是什麼呢?比如說資源的隔離和管理。而且Docker在0.9之前,它的容器運行時是LXC,在0.9之後,他就開始把LXC替換掉,替換成了libcontainer,而這個libcontainer其實就是我們在上文提到的Google的 LMCTFY。再之後libcontainer捐給了OCI。而那之後Docker現在的容器運行時是什麼呢?是containerd。containerd的更下層是runc,runc的核心其實就是libcontainer。

而到了2014年的時候, Google發現大多數的容器化解決方案,其實都只提供了單機的解決方案,同時由於Docker也是CS架構的,所以它需要有一個Docker demand,它是需要有守護進程存在的,而這個守護進程的話,是需要用root用戶去啓動的,而root用戶啓動的守護進程,其實是增加了被攻擊面,所以 Docker的安全問題也被很多人詬病。

在這個時候 Google就發現了這個點,並且把自己的Borg系統去做了開源,開源版本就是Kubernetes。Google還聯合了一些公司,組建了一個雲原生基金會(CNCF)。

圖片

7、Kubernetes

通常來講Kubernetes是雲原生應用的基石,也就是說在Kubernetes出現之後,我們的雲原生技術開始逐步地發展起來,逐步地引領了潮流,Kubernetes提供了一些主要的特性。

它可以支持比較靈活的調度、控制和管理,而這個調度程序的話,除了它默認的以外,也可以比較方便的去對它做擴展,比如說我們可以自己去寫自己的調度程序,或者說親和性、反親和性,這些其實都是我們比較常用到的一些特性。

還有包括他提供的一些服務,比如說內置的 DNS、kube-DNS或者說現在的CoreDNS,通過域名的方式去做服務發現,以及Kubernetes當中有很多的控制器。它可以將集羣的狀態調整至我們預期的狀態,就比如說有一個pod掛掉了,它可以自動的把它再恢復到我們預期想要的樣子。

另外就是它支持豐富的資源種類,比如說幾個主要的層級,最小的是pod,再往上有deployment,或者有StatefulSets,類似於這樣子的資源。

最後一點是它讓我們更加喜歡它的因素,就是它有豐富的CRD的拓展,即可以通過自己去寫一些自定義的資源,然後對它進行擴展,比如CRD。

圖片

8、更多的容器化技術

除了剛纔我們提到的這些主要的技術以外,其實還有很多我們沒有提到的一些容器化的技術,比如說像runc,上文我們沒有太多的介紹,還有containerd。containerd其實也是Docker開源出來的自己的核心,他的目標是做一個標準化工業可用的容器運行時,還有CoreOS開源出來的解決方案叫做rkt。而rkt瞄準的點就是上文提到的Docker相關的安全問題。但是rkt現在項目已經終止了。

還有紅帽(Red Hat)開源出來的 podman, podman是一種可以用它來啓動容器,可以用它去管理容器,而且沒有守護進程,所以就安全性來講的話,podman可以說比Docker的安全性直觀上來看的話會好一些,但是它的便捷性來講的話,就要大打折扣了。比如說容器的重啓、開機起之類的,但是我們都是有一些不同的解決方案的。

在2017年的時候,這個時候有一個 Kata Container,而這個Kata Container它有一段發展過程,最開始是英特爾,英特爾在搞自己的容器運行時,還有一家初創公司叫做hyper.sh,這家公司也在搞自己的容器運行時,這兩家公司瞄準的都是做更安全的容器,他們使用的底層的技術都是基於K8S。而之後這兩家公司做了合併,hyper.sh它開源出來的一個解決方案是runv,被英特爾看上了之後就誕生了 Kata Container。在2018年的時候,AWS開源出來自己的Firecracker。

這兩項技術和我們上文提到的機器上的容器化技術其實大有不同,因爲它的底層其實相當於是虛擬機,而我們通常來講,都認爲它是輕量級虛擬機的一種容器化的技術。以上就是關於多樣的容器化技術的介紹。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章