第一篇 : Docker的基本概念和框架
一、Docker簡介
什麼是容器 ?
- 一種虛擬化的方案
- 作業系統級別的虛擬化
- 只能執行相同或相似的核心作業系統
- 依賴於Linux核心特性:Namespace和Cgroups(Control Group)
容器技術有哪些優點 ?
從圖中我們很容器看出,容器技術資源佔用比較少,由於虛擬機器需要模擬硬體的行為,對CUP和記憶體的損耗比較大。所以同樣配置的伺服器,容器技術就有以下優點:
- 資源佔用比較少
- CPU/記憶體消耗低
那既然容器有這些優點,為什麼直到Docker的出現,才真正的被關注呢?一個重要原因就是容器技術的複雜性。容器本身就很複雜,他依賴於Linux核心的很多特性,而且他不易安裝,也不易於管理和實現自動化。而Docker就是為了改變這一切而產生的。
什麼是Docker ?
- 將應用自動部署到容器的開源引擎
- Go語言實現的開源專案,誕生於2013年初,最初發起者是dotCloud公司
Docker的特點
- 提供簡單輕量的建模方式:簡單,Docker非常容器上手,使用者只需要幾分鐘,就能把自己的專案Docker化。
- 職責的邏輯分離:使用Docker,開發人員只需要關心容器中執行的程式,運維人員只需要關心如何管理容器;Docker設計的目的就是加強開發人員寫程式碼的環境與應用程式要部署的生成環境的一致性。
- 快速高效的開發生命週期:Docker的目標之一是縮短程式碼開發到測試到部署上線的執行週期,讓應用程式具備可移植性,在容器中開發,以容器的形式交付和分發,這樣開發、測試、生產,都使用相同的環境,這樣也就避免了額外的除錯和部署上的開銷,這樣就能有效的縮短產品的上線週期。
- 鼓勵使用面向服務的架構:Docker推薦單個容器只執行一個應用程式或者程序,這樣就形成了一個分散式的應用程式模型,在這種模式下應用程式或服務都可以表述為一系列內部互聯的容器,從而使分散式部署應用程式擴充套件或除錯都變得非常簡單。這就像我們開發中常用的思想;高內聚,低耦合,單一任務。這樣就能避免在同一伺服器上部署不同服務時,可能帶來的服務之間相互影響。這樣服務執行中出現問題時,也比較容易定位問題的所在。
Docker的使用場景
- 使用Docker容器開發、測試、部署服務:因為Docker本身非常輕量化,所以本地開發人員可以構建、執行並分享Docker容器。容器可以在開發環境中建立,然後再提交到測試,最終進入生產環境。
- 建立隔離的執行環境:在很多企業應用中,同一服務的不同版本可能服務於不同的使用者,那麼使用Docker非常容易建立不同的生成環境來執行不同的服務。
- 搭建測試環境:由於Docker的輕量化,所以開發者很容易利用Docker在本地搭建測試環境,用來測試程式在不用系統下的相容性;甚至搭建叢集的部署測試。
- 構建多使用者的平臺即服務(PaaS)基礎設施。
- 提供軟體即服務(SaaS)應用程式。
- 高效能、超大規模的宿主機部署。
二、Docker的基本組成
Docker 包含了一下幾個重要主要部分:
- Docker Client 客戶端
- Docker Daemon 守護程序
- Docker Image 映象
- Docker Container 容器
- Docker Registry 倉庫
Docker 客戶端 / 守護程序
- Docker是C/S架構的程式:Docker客戶端向Docker伺服器端,也就是Docker的守護程序發出請求,守護程序處理完所有的請求工作並返回結果。
- Docker 客戶端對伺服器端的訪問既可以是本地也可以通過遠端來訪問。
Docker Image 映象
- 映象是Docker容器的基石,容器基於映象啟動和執行。映象就好比容器的原始碼,儲存了用於啟動容器的各種條件。
- Docker映象是一個層疊的只讀檔案系統。
- Docker映象使用聯合載入技術
docker的映象是一個層疊的只讀檔案系統,最低端是一個引導檔案系統(即bootfs),第二層是root檔案系統(即rootfs),它位於bootfs之上,可以是一種或多種作業系統,比如ubuntu或者centos。在docker中,root檔案系統永遠只能是隻讀狀態,並且docker運用聯合載入技術又會在root檔案系統之上載入更多的只讀檔案系統,聯合載入指的是一次載入多個檔案系統,但是在外面看起來只能看到一個檔案系統,聯合載入會將各層檔案系統疊加到一起,這樣最終的檔案系統會包含所有的底層檔案和目錄,docker將這樣的檔案系統稱為映象。
Docker Container 容器
- 容器通過映象來啟動,Docker的容器是Docker的執行來源,容器中可以執行客戶的一個或多個程序,如果說映象是Docker宣告週期中的構建和打包階段,那麼容器則是啟動和執行階段。
當一個容器啟動時,docker會在該映象的最頂層載入一個讀寫檔案系統,也就是一個可寫的檔案層,我們在docker執行的程式,就是在這個層中進行執行的,當docker第一次啟動一個容器時,初始的讀寫層是空的,當檔案系統發生變化時,這些變化都會應用到這一層上,比如像修改一個檔案,該檔案首先會從讀寫層下面的只讀層複製到該讀寫層,該檔案的只讀版本依然存在,但是已經被讀寫層中的該檔案副本所隱藏,這就是docker的一個重要技術:寫時複製(copy on write)。每個只讀映象層都是隻讀的,永遠不會變化,當建立一個新容器時,docker會構建出一個映象棧,如下圖所示:
Docker Registry 倉庫
- docker用倉庫來儲存使用者構建的映象,倉庫分為公有和私有兩種,Docker公司提供了一個公有的倉庫Docker Hub。
三、Docker 依賴的 Linux核心特性
Docker依賴於Linux核心的兩個重要特性:
- Namespaces 名稱空間
- Control groups (cgroups) 控制組
Namespaces 名稱空間
很多程式語言都包含了“名稱空間”的概念,我們可以認為“名稱空間”是一種“封裝”的概念, 而“封裝”本身實際上實現的是程式碼的隔離。而在作業系統中,名稱空間提供的是系統資源的隔離,而系統資源包括了程序、網路、檔案系統等。
我們從Docker公開的文件來看,它使用了5種名稱空間:
- PID(Process ID) 程序隔離
- NET(Network)管理網路介面
- IPC(InterProcess Communication)管理跨程序通訊的訪問
- MNT(Mount)管理掛載點
- UTS(Unix Timesharing System) 隔離核心和版本標識
那麼,這些隔離的資源,是如何被管理起來的呢?這就需要用到——Control groups(cgroup)控制組了。
Control groups (cgroups) 控制組
Control groups是Linux核心提供的,一種可以限制、記錄、隔離程序組所使用的物理資源的機制。
最初是由google工程師提出,並且在2007年時被Linux的核心的2.6.24版本引進。可以說,Control groups就是為容器而生的,沒有Control groups就沒有容器技術的今天。
Control groups提供了以下功能:
-
資源限制:例如,memory(記憶體)子系統可以為程序組設定一個記憶體使用的上限,一旦程序組使用的記憶體達到了限額,該程序組再發出記憶體申請時,就會發出“out of memory”(記憶體溢位)的警告。
-
優先順序設定:它可以設定哪些程序組可以使用更大的CPU或者磁碟IO的資源。
-
資源計量:它可以計算程序組使用了多少系統資源。尤其是在計費系統中,這一點十分重要。
-
資源控制:它可以將程序組掛起或恢復。
Namespace 和 cgroup帶給Docker的能力
到這裡我們瞭解了Namespace和CGroup的概念和職能,而這兩個特性帶給了Docker哪些能力呢?如下:
-
檔案系統隔離:首先是檔案系統的隔離,每個Docker的容器,都可以擁有自己的root檔案系統。
-
程序隔離:每個容器都執行在自己的程序環境中。
-
網路隔離:容器間的虛擬網路介面和IP地址都是分開的。
-
資源的隔離和分組:使用cgroups將cpu和記憶體之類的資源獨立分配給每個Docker容器。