docker(2) 基礎知識整理及原理

2021-10-08 20:54:15 字數 3384 閱讀 5312

命名空間(namespaces)是 linux 為我們提供的用於分離程序樹、網路介面、掛載點以及程序間通信等資源的方法。

docker 其實就通過 linux 的 namespaces 對不同的容器實現了隔離。

linux 的命名空間機制提供了以下七種不同的命名空間,包括 clone_newcgroup、clone_newipc、clone_newnet、clone_newns、clone_newpid、clone_newuser 和 clone_newuts,通過這七個選項我們能在建立新的程序時設定新程序應該在哪些資源上與宿主機器進行隔離。

control groups(簡稱 cgroups)就是能夠隔離宿主機器上的物理資源,例如cpu、記憶體、磁碟 i/o 和網路頻寬

每乙個 cgroup 都是一組被相同的標準和引數限制的程序,不同的 cgroup 之間是有層級關係的,也就是說它們之間可以從父類繼承一些用於限制資源使用的標準和引數。

unionfs 其實是一種為 linux 作業系統設計的用於把多個檔案系統『聯合』到同乙個掛載點的檔案系統服務。而 aufs 即 advanced unionfs 其實就是 unionfs 的公升級版,它能夠提供更優秀的效能和效率。

aufs 作為聯合檔案系統,它能夠將不同資料夾中的層聯合(union)到了同乙個資料夾中,這些資料夾在 aufs 中稱作分支,整個『聯合』的過程被稱為聯合掛載(union mount):

2.1 linux的1號程序

docker 的 stop 和 kill 命令都是用來向容器傳送訊號的。注意,只有容器中的 1 號程序能夠收到訊號,這一點非常關鍵!

在docker容器中的初始化程序(pid1程序)在容器程序管理上具有特殊意義。它可以被dockerfile中的entrypointcmd指令所指明;也可以被docker run命令的啟動引數所覆蓋。了解這些細節可以幫助我們更好地了解pid1的程序的行為

2.2 dockerfile中  cmd、entrypoint區別

cmd 指令的目的是:為容器提供預設的執行命令。

cmd 指令有三種使用方式,其中的一種是為 entrypoint 提供預設的引數:

cmd ["param1","param2"]

另外兩種使用方式分別是 exec 模式和 shell 模式:

cmd ["executable","param1","param2"]    // 這是 exec 模式的寫法,注意需要使用雙引號。

cmd command param1 param2                  // 這是 shell 模式的寫法。

注意命令列引數可以覆蓋 cmd 指令的設定,但是只能是重寫,卻不能給 cmd 中的命令通過命令列傳遞引數。

一般的映象都會提供容器啟動時的預設命令,但是有些場景中使用者並不想執行預設的命令。使用者可以通過命令列引數的方式覆蓋 cmd 指令提供的預設命令。比如通過下面命令建立的映象:

docker run的命令會覆蓋cmd的命令

entrypoint 指令的目的也是為容器指定預設執行的任務。

entrypoint 指令有兩種使用方式,就是我們前面介紹的 exec 模式和 shell 模式:

entrypoint ["executable", "param1", "param2"]   // 這是 exec 模式的寫法,注意需要使用雙引號。

entrypoint command param1 param2                   // 這是 shell 模式的寫法。

exec 模式和 shell 模式的基本用法和 cmd 指令是一樣的,下面我們介紹一些比較特殊的用法。

指定 entrypoint  指令為 exec 模式時,命令列上指定的引數會作為引數新增到 entrypoint 指定命令的引數列表中。用下面的**構建映象 test1:

docker run的命令不會覆蓋entrypoint 命令

同時使用:

我們大概可以總結出下面幾條規律:

• 如果 entrypoint 使用了 shell 模式,cmd 指令會被忽略。

• 如果 entrypoint 使用了 exec 模式,cmd 指定的內容被追加為 entrypoint 指定命令的引數。

• 如果 entrypoint 使用了 exec 模式,cmd 也應該使用 exec 模式。

摘抄自:dockerfile實踐指南之層數與大小的控制

dockerfile中,每一行的命令都會生成乙個新層

注意:1. /etc/hosts檔案在每一層都恢復原狀

2. docker在啟動容器時建立/ etc / hosts檔案.這就是為什麼我的/ etc / hosts檔案的修改被覆蓋了

引入了層的概念,即使用者在製作映象時的每一步操作都會生成乙個層,也就是增量的 rootfs

docker 映象的層分為唯讀層、可讀寫層和 init 層

1、唯讀層包含了整個底層作業系統所必須的一些目錄和依賴

2、可讀寫層沒寫入檔案之前,這個目錄是空的。而一旦有了寫操作,修改的內容就會以增量的方式出現在這層中

3、init 層用來存放一些例如 /etc/hosts、/etc/resolv.conf等資訊

dockerfile構建映象時每個命令的操作都會建立乙個新的層,最終組成目的映象

當容器啟動時,乙個新的可寫層被載入到映象的頂部。這一層通常被稱作「容器層」,「容器層」之下的都叫「映象層」

映象層數量可能會很多,所有映象層會聯合在一起組成乙個統一的檔案系統。如果不同層中有乙個相同路徑的檔案,比如 /a,上層的 /a 會覆蓋下層的 /a,也就是說使用者只能訪問到上層中的檔案 /a。在容器層中,使用者看到的是乙個疊加之後的檔案系統。

新增檔案:在容器中建立檔案時,新檔案被新增到容器層中。

讀取檔案:在容器中讀取某個檔案時,docker 會從上往下依次在各映象層中查詢此檔案。一旦找到,立即將其複製到容器層,然後開啟並讀入記憶體。

修改檔案:在容器中修改已存在的檔案時,docker 會從上往下依次在各映象層中查詢此檔案。一旦找到,立即將其複製到容器層,然後修改之。

刪除檔案:在容器中刪除檔案時,docker 也是從上往下依次在映象層中查詢此檔案。找到後,會在容器層中記錄下此刪除操作。

只有當需要修改時才複製乙份資料,這種特性被稱作 copy-on-write。可見,容器層儲存的是映象變化的部分,不會對映象本身進行任何修改。

這樣就解釋了我們前面提出的問題:容器層記錄對映象的修改,所有映象層都是唯讀的,不會被容器修改,所以映象可以被多個容器共享。

C 基礎知識整理 基礎知識(2) 類

類,是物件導向語言的基礎。類的三大特性 封裝 繼承 多型。最基本的特性就是封裝性。程式設計師用程式描述世界,將世界的所有事物都看成物件,怎麼描述這個物件?那就是類了。也就是用類來封裝物件。用書上的話說,類是具有相同屬性和行為的物件的抽象。寶馬汽車 別克汽車 五菱之光汽車.基本具有相同的屬性和行為,所...

C 基礎知識整理 基礎知識(2) 類

類,是物件導向語言的基礎。類的三大特性 封裝 繼承 多型。最基本的特性就是封裝性。程式設計師用程式描述世界,將世界的所有事物都看成物件,怎麼描述這個物件?那就是類了。也就是用類來封裝物件。用書上的話說,類是具有相同屬性和行為的物件的抽象。寶馬汽車 別克汽車 五菱之光汽車.基本具有相同的屬性和行為,所...

Java基礎知識整理2

1.public string trim 乙個字串s通過呼叫方法trim 得到乙個字串物件,該字串物件是s去掉前後空格後的字串 2.public string substring int start,int end 字串物件呼叫該方法獲得乙個當前字串的子串,該子串是從當前字串的start處擷取到en...