當前位置: 妍妍網 > 碼農

【運維幹貨分享】什麽是容器,它是如何工作的?

2024-07-27碼農


container

如果想了解什麽是容器以及它們如何工作?

這篇文章解釋了容器化的基礎知識,包括定義、優點和用例。

如果你剛了解容器世界,那麽學習基礎知識至關重要。

這將幫助你有效地學習Docker等工具和Kubernetes等編排工具

我們先從linux容器聊起。

什麽是容器?

在典型的虛擬化環境中,一個或多個虛擬機器使用 Xen、Hyper-V 等虛擬機器管理程式執行在物理伺服器之上。

另一方面,容器執行在作業系統內核之上。可以將其稱為作業系統級虛擬化。在了解底層容器概念之前,需要了解兩個關鍵的 Linux 概念。

使用者空間

使用者空間:執行使用者程式(應用程式、行程)所需的所有程式碼稱為使用者空間。當您啟動程式操作(例如建立檔)時,使用者空間中的行程會對內核空間進行系統呼叫。

內核空間

內核空間:這是作業系統的核心,其中包含內核程式碼,與系統硬體、儲存等進行互動。

容器行程隔離

當啟動一個應用程式(例如 Nginx Web 伺服器)時,實際上是在啟動一個行程。行程是一組獨立的指令,具有有限的隔離性。

但是,如果可以隔離該行程以及僅執行和操作該行程所需的檔和配置,該怎麽辦?這正是容器的作用。

透過為流程建立隔離的環境,容器可以在不同系統之間實作更高的安全性、一致性和可移植性。

當容器啟動時,它會在主機作業系統的內核中啟動一個行程。然而,值得註意的是,容器不僅僅是一個行程——它可以包含並列執行的多個行程和服務,所有這些都在同一個隔離環境中。

因此,雖然容器確實作為一個行程啟動,但它並不僅限於單個行程。它是一個更復雜的系統,可以包含多個流程和服務,使其成為軟體開發和部署的更通用的解決方案。

例如,當啟動 Nginx 服務時,它會啟動一個 Nginx 父行程,該行程會生成緩存管理器、緩存載入器和工作行程等子行程

啟動 Nginx 容器時,將在其自己的隔離環境中啟動主 Nginx 行程。

每個容器都有自己獨立的使用者空間,可以在單個主機上執行多個容器。然而,需要註意的是,容器並不擁有整個作業系統。

與具有自己的內核的虛擬機器不同,容器僅包含與特定發行版相關的必要檔,並使用共享的主機內核。

事實上,可以在單個主機上執行基於不同 Linux 發行版的容器,所有容器共享相同的內核空間。這使得容器成為在隔離環境中執行應用程式的輕量級且高效的解決方案。

例如,可以在 Ubuntu 伺服器上執行基於 RHEL、CentOS 或 SUSE 的容器。這是因為 Linux 發行版之間的唯一區別是使用者空間,而內核空間保持不變

容器是單行程嘛?

一個容器可以有多個父行程嗎?

不可以,一個容器不能有多個父行程。容器執行一個主行程,該行程在容器啟動時啟動。主行程負責啟動和管理容器需要執行的任何子行程。

為什麽只有一個父行程?

容器主要設計為每個容器執行一個行程。

這樣做的原因是為了促進隔離並保持容器的穩定性。當單個行程在容器中執行時,與該行程相關的任何更改或問題只會影響執行該行程的容器,而不會影響其他容器或主機系統。

例如,假設想要執行一個帶有 Web 伺服器和資料庫的 Web 應用程式。我們不需要在單個容器中執行 Web 伺服器和資料庫,而是需要在同一主機上的單獨容器中執行它們。

例如,如果 Web 伺服器程式碼中存在錯誤或漏洞,它不會影響其他容器或主機系統,因為 Web 伺服器在容器內是隔離的。

同樣,如果對 Web 伺服器配置或設定進行更改,它只會影響執行該行程的容器,而不會影響其他容器或主機系統。這促進了容器的隔離性和可維護性,使其更易於管理和部署。

是否可以在容器內執行多個行程?

透過執行行程管理器(例如supervisord)可以在容器內執行多個行程。

行程管理器充當容器的主行程,它可以生成和管理多個子行程。這允許多個服務或行程在單個容器內執行,但它們全部由單個父行程(行程管理器)管理。

名稱空間和控制組

容器的隔離是透過使用兩個關鍵的 Linux 內核功能來實作的

  • namespaces

  • cgroup

  • 這個概念在現實世界中的一個有用的類比是公寓樓。雖然它是一棟大型建築,但每個公寓或公寓都是獨立的,每個家庭都有自己的身份和計量公用設施。這種隔離是透過使用混凝土、鋼結構和其他材料來實作的。除非被邀請進入,否則您無法看到其他房屋的內部。

    同樣,在具有多個容器的單個主機中,您需要將容器與其自己的CPU、記憶體、IP地址、掛載點和行程隔離。這是透過使用 Linux 內核中的名稱空間和控制組來實作的。

    Linux 名稱空間

    容器就是擁有一個良好隔離的環境來執行服務(行程)。

    為了實作這種級別的隔離,容器應該有其檔案系統、IP 地址、掛載點、行程 ID 等。這可以使用 Linux 名稱空間來實作。Linux 名稱空間概念被添加到 Linux 內核版本 2.4.19 中,該版本於 2002 年 12 月 18 日釋出。這是 Wikipedia 關於 Linux 名稱空間的描述。

    名稱空間是 Linux 內核的一項功能,它對內核資源進行分區,以便一組行程看到一組資源,而另一組行程看到一組不同的資源。

    Linux 中的關鍵名稱空間包括:

  • PID namespace 負責隔離行程(PID:行程ID)

  • Network namespace 管理網路介面(NET:網路)

  • IPC namespace 管理對IPC資源的存取(IPC:行程間通訊)

  • Mount namespace 負責管理檔案系統掛載點(MNT:Mount)

  • uts namespace 隔離內核和版本識別元(UTS:Unix 分時系統)

  • usr namespace 隔離使用者 ID,這意味著它將主機和容器之間的使用者 ID 分開。

  • Control Group namespace 將控制組資訊與容器行程隔離。

  • 使用這些名稱空間,容器可以擁有其網路介面、IP 地址等。每個容器都有其名稱空間,並且在該名稱空間內執行的行程不會擁有其外部的任何特權。

    本質上,名稱空間為容器設定邊界。

    有趣的是,您可以使用 lsns 命令列出 Linux 電腦中的名稱空間。

    lsns

    Linux 控制組

    在 Linux 系統上啟動服務不需要指定任何記憶體或 CPU 限制。內核自動分配資源並為正在執行的服務確定優先級。

    但是,如果想對服務的 CPU 和記憶體使用情況設定明確的限制,則可以使用稱為控制組 (CGroup) 的 Linux 內核功能。

    當在一台主機上執行多個容器時,這一點特別有用,因為它可以確保一個容器不會過度利用資源而犧牲其他容器的資源。

    CGroup 管理容器使用的資源,並允許您限制容器的 CPU、記憶體、網路和 I/O 資源。如果沒有資源限制,單個容器可能會使用所有可用的主機資源,從而導致其他容器資源不足並導致它們崩潰。

    值得慶幸的是,像 Docker 這樣的工具透過抽象出復雜的後端配置來簡化設定資源限制的過程。

    借助 Docker,您可以使用簡單的參數輕松指定 CPU 和記憶體限制,確保容器高效可靠地執行。

    容器的演變

    盡管有些人可能這麽認為,容器化並不是一項新技術。事實上,谷歌多年來一直在其基礎設施中使用容器技術。容器的概念實際上可以追溯到 20 世紀 70 年代,當時引入了 chroot,這是一個允許更改行程根目錄的概念。從那時起,開發了許多基於容器的計畫,其中一些早在 2000 年就開始了。

    容器與虛擬機器

    下圖顯示了容器和虛擬機器之間的主要區別。

    與虛擬機器 (VM) 相比,容器具有多種優勢,使其成為部署應用程式的熱門選擇:

    資源利用和成本:

    虛擬機器允許獨立執行應用程式,但它們可能未得到充分利用,並且為生產應用程式調整虛擬機器的大小可能具有挑戰性。

    相比之下,容器需要最少的 CPU 和記憶體資源,並且可以在虛擬機器內執行多個容器,以實作更好的應用程式隔離。調整容器大小只需幾秒鐘,使其更加高效且更具成本效益。

    配置和部署:

    配置虛擬機器並在其上部署應用程式可能需要幾分鐘到幾小時,具體取決於所涉及的工作流程。即使回滾更改也需要時間。相比之下,容器可以秒級部署,回滾也同樣快,更加敏捷高效。

    漂移管理

    管理虛擬機器中的偏差很困難,需要大量的自動化和流程來確保所有環境都是相似的。然而,遵循不可變的部署模型可以防止虛擬機器環境中的偏差。另一方面,容器只需要更新容器映像即可進行更改。透過對開發環境進行更改並重新烘焙容器映像,可以確保所有環境中使用相同的映像。這使得管理漂移變得更容易、更高效。

    結論

    我們了解了容器的核心基礎以及它與虛擬機器的不同之處。接下來我們就可以開始使用以下教程

  • 什麽是 Docker 以及它是如何工作的?

  • 如何構建 Docker 映像並執行 Docker 容器?

  • 如何最佳化Docker映像?

  • 轉譯自:https://devopscube.com/what-is-a-container-and-how-does-it-work/