docker常用命令
上圖是Docker的架構(gòu)
整個(gè)Docker由客戶(hù)端、服務(wù)端和倉(cāng)庫(kù)構(gòu)成
常用命令
docker images docker search imagename docker pull imagename:tag docker rmi id/name docker ps docker run -it -p port1:port2 image docker exec -it containername docker stop containername docker start containername docker cp file containername:dir docker cp containername:dir file docker inspect containername docker rm containername docker volume ls docker save -o image docker load xx.tar.gz
docker與虛擬機(jī)
docker出現(xiàn)的原因主要是解決傳統(tǒng)的開(kāi)發(fā)和運(yùn)維方面的問(wèn)題
case one:開(kāi)發(fā)環(huán)境和生產(chǎn)環(huán)境可能不一致的問(wèn)題,就比如一個(gè)項(xiàng)目剛開(kāi)發(fā)的時(shí)候使用的MySQL是5.5版本,之后經(jīng)過(guò)幾輪開(kāi)發(fā),MySQL版本升級(jí)到了5.7,這個(gè)時(shí)候測(cè)試的版本還是5.5,在沒(méi)有虛擬化技術(shù)之前,測(cè)試只有兩個(gè)辦法 1.刪了重裝 2.多裝一個(gè) 就很麻煩。但虛擬化技術(shù)出現(xiàn)之后,直接遠(yuǎn)程docker pull,幾分鐘之內(nèi)就能構(gòu)建出一個(gè)MySQL5.7的環(huán)境
case two:在不同的開(kāi)發(fā)環(huán)境中構(gòu)建和運(yùn)行應(yīng)用程序可能會(huì)遇到很多問(wèn)題。Docker可以將應(yīng)用程序和依賴(lài)項(xiàng)打包到一個(gè)可移植的容器中,從而使得開(kāi)發(fā)環(huán)境的設(shè)置變得更加簡(jiǎn)單和重復(fù)
case three:從安全性和速度上來(lái)說(shuō)也比傳統(tǒng)運(yùn)維更加簡(jiǎn)單,可以很輕松的起成百上千個(gè)容器,并且這些容器在操作系統(tǒng)級(jí)別和硬件級(jí)別都存在隔離
一句話(huà)概括:通過(guò)Docker我們可以將**程序運(yùn)行的環(huán)境也納入到控制中 **
docker和虛擬機(jī)有何區(qū)別
docker絕對(duì)不是輕量級(jí)的虛擬機(jī) 絕對(duì)不是
docker是一個(gè)client-server結(jié)構(gòu)的應(yīng)用,守護(hù)進(jìn)程運(yùn)行在主機(jī)上,然后通過(guò)socket連接從客戶(hù)端訪問(wèn)docker守護(hù)進(jìn)程
一個(gè)docker容器,是一個(gè)運(yùn)行時(shí)的環(huán)境,可以簡(jiǎn)單理解成進(jìn)程運(yùn)行的集裝箱
docker和kvm(linux的內(nèi)核虛擬機(jī))都是虛擬化技術(shù),主要差別在于:
docker比虛擬機(jī)更少的抽象層,docker更加輕便和低成本
docker利用宿主機(jī)內(nèi)核 kvm需要guest os(直接在Host OS上多建一個(gè)OS),docker以MB硬盤(pán)為單位,kvm以GB為單位
在啟動(dòng)速度上 docker是秒級(jí)別的,而KVM是分鐘級(jí)別的,和KVM相比,docker應(yīng)用的性能高,同時(shí)系統(tǒng)的開(kāi)銷(xiāo)小
KVM在宿主機(jī)器的基礎(chǔ)上創(chuàng)建虛擬層、來(lái)賓操作系統(tǒng)、虛擬化倉(cāng)庫(kù),然后安裝應(yīng)用
容器在宿主機(jī)操作系統(tǒng)上創(chuàng)建docker引擎,在引擎的基礎(chǔ)上安裝應(yīng)用
所以虛擬機(jī)是分鐘級(jí)別 容器是秒級(jí)別
最核心的一點(diǎn)是:Docker和傳統(tǒng)的VM虛擬機(jī)作比較的話(huà),并不需要硬件的支持,只是進(jìn)行了內(nèi)核級(jí)別的虛擬化,像VM虛擬機(jī)是和真正的物理機(jī)器一樣,對(duì)各種硬件都進(jìn)行了虛擬化
docker技術(shù)底座
Linux命名空間 namespace 、控制組cgroup和unionFS union file system三大技術(shù)支撐了目前Docker的實(shí)現(xiàn) 也是Docker能夠出現(xiàn)的最重要原因
namespace
在linux中,namespace是在內(nèi)核級(jí)別實(shí)現(xiàn)資源隔離的手段,不同的namespace程序可以享有一份獨(dú)立的系統(tǒng)資源
namespace是linux為我們提供的用于分離進(jìn)程樹(shù)、網(wǎng)絡(luò)接口、掛載點(diǎn)、進(jìn)程通信等資源的方法,在日常使用linux的時(shí)候,如果我們?cè)诜?wù)器上啟動(dòng)了多個(gè)服務(wù),這些服務(wù)其實(shí)是會(huì)相互影響的,因?yàn)樗麄兡芑ハ嗫梢?jiàn),也可以訪問(wèn)宿主機(jī)上的任意文件,但我們更希望一臺(tái)機(jī)器上的不同服務(wù)能做到完全隔離,就像運(yùn)行在不同的機(jī)器上一樣。Docker通過(guò)使用namespace來(lái)實(shí)現(xiàn)容器的隔離,每個(gè)容器都有自己的namespace,可以訪問(wèn)其內(nèi)部資源而不會(huì)影響宿主機(jī)或者其他容器,這使得Docker可以輕松地創(chuàng)建、啟動(dòng)和停止容器
在這種環(huán)境下,一旦服務(wù)器的某一個(gè)服務(wù)被入侵,那么入侵者就能夠訪問(wèn)當(dāng)前機(jī)器上的所有服務(wù)和文件
通過(guò)這七個(gè)選項(xiàng) 我們能設(shè)置新的進(jìn)程在哪些資源上和宿主機(jī)進(jìn)行隔離
fork:當(dāng)調(diào)用fork函數(shù)時(shí),系統(tǒng)會(huì)創(chuàng)建新的進(jìn)程為其分配資源,例如存儲(chǔ)數(shù)據(jù)和代碼的空間,然后把原來(lái)的進(jìn)程值都賦值到新的進(jìn)程中,只有少量值與原來(lái)不同,相當(dāng)于克隆自己fork的返回值在父進(jìn)程中:fork返回子進(jìn)程的ID在子進(jìn)程中:fork返回0
如果錯(cuò)誤:fork返回一個(gè)負(fù)值
Linux的命名空間機(jī)制提供了以下其中不同的命名空間,包括
CLONE_NEW CGROUP
CLONE_NEW IPC 提供一個(gè)獨(dú)立的進(jìn)程間通信的機(jī)制,信號(hào)量、共享內(nèi)存、消息隊(duì)列等只在容器內(nèi)部課見(jiàn)
CLONE_NEW NET 為容器提供一個(gè)獨(dú)立的網(wǎng)絡(luò)環(huán)境,使得容器內(nèi)部的網(wǎng)絡(luò)接口、IP地址、路由表和防火墻規(guī)則都只能在容器內(nèi)部可見(jiàn)
CLONE_NEW NS
CLONE_NEW PID 容器的獨(dú)立進(jìn)程ID空間,容器內(nèi)部的進(jìn)程只能看到自己的進(jìn)程ID,而不會(huì)影響宿主機(jī)或者其他容器的進(jìn)程
CLONE_NEW USER 容器內(nèi)的獨(dú)立用戶(hù)和用戶(hù)組
CLONE_NEW UTS 容器內(nèi)的獨(dú)立主機(jī)名和域名
通過(guò)這些選項(xiàng),我們可以在創(chuàng)建新的進(jìn)程時(shí)設(shè)置哪些資源與宿主機(jī)器進(jìn)行隔離
Linux最特殊的兩個(gè)進(jìn)程:pid為1的/sbin/init的進(jìn)程,和pid為2的kthreadd進(jìn)程,這兩個(gè)進(jìn)程都是被Linux的上帝進(jìn)程idle創(chuàng)建出來(lái)的,前者負(fù)責(zé)執(zhí)行內(nèi)核的一部分初始化工作和系統(tǒng)配置,后者負(fù)責(zé)管理和調(diào)度其他的內(nèi)核進(jìn)程
當(dāng)我們運(yùn)行docker run或者docker start的時(shí)候,就會(huì)啟動(dòng)setNamespaces方法,設(shè)置進(jìn)程、用戶(hù)、網(wǎng)絡(luò)和IPC相關(guān)的命名空間,然后作為Create的參數(shù)在創(chuàng)建新容器的時(shí)候完成設(shè)置
如果docker的容器通過(guò)Linux的命名空間完成了和宿主機(jī)進(jìn)程的網(wǎng)絡(luò)隔離,但是又沒(méi)有辦法通過(guò)宿主機(jī)的網(wǎng)絡(luò)與整個(gè)互聯(lián)網(wǎng)相連,就會(huì)產(chǎn)生很多限制,所以Docker中的服務(wù)還是需要與外界連接才能發(fā)揮作用,每一個(gè)用docker run啟動(dòng)的容器都具有單獨(dú)的網(wǎng)絡(luò)命名空間,Docker為我們提供了四種不同的網(wǎng)絡(luò)模式
Host
Container
None
Bridge
Docker默認(rèn)的網(wǎng)絡(luò)設(shè)置模式:網(wǎng)橋模式,在這種模式下除了分配隔離的網(wǎng)絡(luò)命名空間之外,Docker還會(huì)為所有的容器設(shè)置IP地址,當(dāng)Docker服務(wù)器啟動(dòng)時(shí),會(huì)創(chuàng)建新的虛擬網(wǎng)橋docker0,docker0會(huì)為每一個(gè)容器分配一個(gè)新的IP地址,并將docker0的IP地址設(shè)置為默認(rèn)的網(wǎng)關(guān),網(wǎng)橋docker0通過(guò)iptables中的配置與宿主機(jī)器上的網(wǎng)卡相連。每當(dāng)有一個(gè)新的服務(wù)需要暴露給宿主機(jī),就會(huì)給容器分配一個(gè)IP地址,同時(shí)向iptables追加一條新的規(guī)則。
Docker通過(guò)Linux的命名空間實(shí)現(xiàn)了網(wǎng)絡(luò)的隔離,又通過(guò)iptables進(jìn)行數(shù)據(jù)包轉(zhuǎn)發(fā),讓Docker容器能夠優(yōu)雅的為宿主機(jī)或者其他容器提供服務(wù)
Cgroup
CGROUP解決的就是限制容器物理資源占用的問(wèn)題
掛載點(diǎn):Docker容器中的進(jìn)程仍然能夠訪問(wèn)或者修改宿主機(jī)上的其他目錄,這是我們不希望看到的。
如果一個(gè)容器需要啟動(dòng),那么它一定需要提供一個(gè)跟文件系統(tǒng)(rootfs),容器需要通過(guò)這個(gè)文件系統(tǒng)來(lái)創(chuàng)建一個(gè)新的進(jìn)程,所有二進(jìn)制的執(zhí)行都必須要在這個(gè)跟文件的系統(tǒng)中。從而實(shí)現(xiàn)將容器需要的目錄掛在到容器中,同時(shí)也禁止當(dāng)前的容器進(jìn)程訪問(wèn)宿主機(jī)器上的其他目錄,保證了不同文件系統(tǒng)的隔離
我們通過(guò)NAMESPACE隔離了文件、網(wǎng)絡(luò)和進(jìn)程,但是不能提供物理資源上的隔離,比如CPU或者內(nèi)存,如果一個(gè)容器正在執(zhí)行CPU密集型的任務(wù),那么就會(huì)影響其他容器的性能和效率,而CGROUPS就是能夠隔離宿主機(jī)器上的物理資源,例如CPU 內(nèi)存 磁盤(pán)IO等等
每一個(gè)CGROUP都是一組被相同標(biāo)準(zhǔn)和參數(shù)限制的進(jìn)程,CGROUP之間有層級(jí)關(guān)系,可以從父類(lèi)進(jìn)程一些標(biāo)準(zhǔn)和參數(shù)
而Cgroup的核心是一個(gè)叫做cgroupfs的文件系統(tǒng),位于linux內(nèi)核中的/sys/fs/cgroup目錄下。該文件系統(tǒng)允許用戶(hù)在一個(gè)層次結(jié)構(gòu)中創(chuàng)建、管理和監(jiān)控cgroup,具體實(shí)現(xiàn)如下
創(chuàng)建cgroup層次結(jié)構(gòu),這個(gè)層次結(jié)構(gòu)由一個(gè)或者多個(gè)cgroup組成,每個(gè)cgroup都代表一組進(jìn)程,并擁有一組資源限制。
將進(jìn)程添加到cgroup中,這個(gè)實(shí)現(xiàn)其實(shí)就是把進(jìn)程加到task文件中
為cgroup分配限制資源,例如可以用cgroup/cpu/相關(guān)的文件來(lái)限制cpu的使用率
監(jiān)控cgroup的資源使用
Union File System
Union File System是一種文件系統(tǒng)技術(shù),可以將多個(gè)文件系統(tǒng)(通常是只讀文件系統(tǒng)和可寫(xiě)文件系統(tǒng))合并成一個(gè)虛擬文件系統(tǒng),使其像一個(gè)文件系統(tǒng),但實(shí)際上是由多個(gè)文件系統(tǒng)組成的。
在Docker中,UFS解決了鏡像只讀不可寫(xiě)的問(wèn)題,同時(shí)也是Docker的基礎(chǔ)文件系統(tǒng)
UFS的實(shí)現(xiàn)基于三種文件系統(tǒng):
只讀文件系統(tǒng)
是UFS的基礎(chǔ),通常包含操作系統(tǒng)的核心組件和基本文件系統(tǒng)。在Docker中,只讀文件系統(tǒng)通常是一個(gè)Docker鏡像提供的
可寫(xiě)文件系統(tǒng)
可寫(xiě)文件系統(tǒng)是一個(gè)額外的文件系統(tǒng)層,它覆蓋在只讀文件系統(tǒng)之上,用于保存容器中創(chuàng)建、修改和刪除的文件。每個(gè)容器都有自己的可寫(xiě)文件系統(tǒng)層,使得容器之間的文件不會(huì)相互干擾,在Docker中,可寫(xiě)層是在容器運(yùn)行時(shí)創(chuàng)建的
合并文件系統(tǒng)
將只讀文件系統(tǒng)和可寫(xiě)文件系統(tǒng)合并而成的,使得容器可以訪問(wèn)只讀文件系統(tǒng)和可寫(xiě)文件系統(tǒng)層中的文件,就像它們是一個(gè)單獨(dú)的文件系統(tǒng)一樣。
在DOCKER中還有另一個(gè)非常重要的問(wèn)題-鏡像
Docker鏡像的本質(zhì)其實(shí)就是一個(gè)壓縮包 也就是一個(gè)文件
Docker鏡像是如何構(gòu)建:Docker中的每一個(gè)鏡像都是由一系列只讀的層組成的,DockerFile中的每一個(gè)命令都會(huì)在已有的只讀層上創(chuàng)建一個(gè)新的層,類(lèi)似于搭積木,鏡像的每一層其實(shí)都只是對(duì)當(dāng)前鏡像進(jìn)行了部分改動(dòng),當(dāng)鏡像被docker run命令創(chuàng)建時(shí),就會(huì)在鏡像的最上層添加一個(gè)可寫(xiě)的層,也就是容器層。
容器和鏡像的區(qū)別就是 鏡像只是可讀的,而每一個(gè)容器其實(shí)等于鏡像加上一個(gè)可讀寫(xiě)的層,也就是同一個(gè)鏡像可以對(duì)應(yīng)多個(gè)容器。
審核編輯:劉清
-
虛擬機(jī)
+關(guān)注
關(guān)注
1文章
937瀏覽量
28426 -
LINUX內(nèi)核
+關(guān)注
關(guān)注
1文章
316瀏覽量
21742 -
KVM
+關(guān)注
關(guān)注
0文章
188瀏覽量
12983 -
UFS
+關(guān)注
關(guān)注
6文章
105瀏覽量
24152 -
Docker
+關(guān)注
關(guān)注
0文章
492瀏覽量
11963
原文標(biāo)題:Docker底層實(shí)現(xiàn) 講解
文章出處:【微信號(hào):magedu-Linux,微信公眾號(hào):馬哥Linux運(yùn)維】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。
發(fā)布評(píng)論請(qǐng)先 登錄
相關(guān)推薦
評(píng)論