我自己的第一個問題是,到底甚麼是 container 呢?他好像是虛擬機器但他又不是虛擬機器,Docker 說他跟虛擬機器不一樣,幾乎沒有 overhead。為了一探究竟,我先看看 iThome 上的說明:
一般常見的虛擬機器和 Container 最明顯的差別是,虛擬機器需要安裝作業系統(安裝Guest OS)才能執行應用程式,而Container內不需要安裝作業系統就能執行應用程式。Container技術不是在OS外來建立虛擬環境,而是在OS內的核心系統層來打造虛擬執行環境,透過共用Host OS的作法,取代一個一個Guest OS的功用。Container也因此被稱為是OS層的虛擬化技術。
但看了之後還是有看沒有懂,虛擬機器 (Virtual Machine) 的概念還蠻好懂的, host OS 透過軟體完整模擬出一個硬體系統,包含指令集、BIOS、中斷處理、I/O等等,讓執行在 host OS 上的 guest OS 以為他真的執行在一個專屬的硬體上,某種程度來說,host OS 和 guest OS 沒有太大的關連,host OS只是出租一塊空間給 guest OS。container 的概念是和 host OS 共用,透過 kernel level 的共用技術打造出的虛擬化技術。但這樣的說明還是無法解決我的疑慮,看來我需要比較技術性的說明,而不只是抽象的描述...
(圖片來源http://jenkins-cookbook.cloudbees.com/docs/jenkins-cookbook)
虛擬機器是提供一個獨立運作的硬體環境,代表的意義是要做甚麼事都是你 guest OS 的事情,擁有非常大的空間,甚至你可以在 Host OS 上藉由 VM安裝多的不同的 guest OS (例如:同時安裝 Windows 和 Ubuntu),上圖中的 hypervisor 就是建立虛擬硬體的系統。
Container 既然是從核心層所打造的虛擬環境,自然在 kernel level 會有相對應的支援功能,主要是由 Linux kernel namespace 和 Control group 兩種主要技術所建立的系統,目的是藉由 kernel 的支援,為 process 建立虛擬的獨立空間,既然他的目標是 process,可想而知所針對的是應用程式,而非像 VM 一樣是完整獨立的虛擬硬體。因此,本篇先針對 container 在 kernel 層的支援做探討,以了解他的運作原理和差異。
Linux kernel namespace
Namespace的目的是要為 LWP (Light Weight Process, 輕量級行程) 建立虛擬空間,意思就是要將每個 LWP 隔離出一個獨立的空間,這樣不同 container 之間的 process 就不會互相干擾。
目前支援以下的 namespaces
- mnt (mount points, filesystems)
- pid (processes)
- net (network stack)
- ipc (System V IPC)
- uts (hostname)
- user (UIDs)
- security namespace
- security keys namespace
- device namespace
- time namespace.
Control groups
Control groups (cgroups) subsystem 是一種資源管理系統,用以對一組 process 做資源的控制,這裡所提到資源可包含 CPU / memory / disk IO / network 等等。透過資源管理,可以設定每個 container 的應用程式能分配到多少資源,讓每個運作在 container 裡的服務都能夠依據其等級得到適當的資源。Cgroups 主要功能有以下幾點:
- 資源限制 (resource limitation) - 例如:你可以控制 /usr/bin/prog_a 的 記憶體使用不得超過 500 MB。
- 優先權控制 (prioritization) - 例如:你可以控制 /usr/bin/prog_a 的 CPU resource 為 20%。
- 帳戶管理 (accounting) - 每個 container 可以視為一個帳戶,透過帳戶管理你可以了解每個 container 的資源使用狀況,甚至可以當作收費的依據。
- 執行控制 (control) - 你可以為 process 設定檢查點 (checkpoint),然後可以暫停或重新執行他。
結論:
透過 namespace 和 control groups 的支援,host OS 可以打造出一個獨立運作的空間讓應用程式執行,並對此獨立空間的程式提供資源的管理,如此可讓不同的獨立空間的程式皆能夠被分配到資源。使用虛擬機器的每個獨立空間皆須重新安裝一個完整的作業系統,硬碟空間 (安裝作業系統需要大量的硬碟空間) 和系統資源上 (特別是 CPU and memory) 的額外需求是非常大的,因此對比虛擬機器,container 能夠大大的節省上述的 overhead 的支出,在同樣的硬體環境下能夠提供比虛擬機器更多的服務。 然而,這並不是 container 的唯一好處而已,之後會針對 container 在執行佈署上的優點再研究討論。