Docker
Docker介紹
http://www.runoob.com/docker/docker-tutorial.html
什么是docker
Docker 是一個(gè)開源的應(yīng)用容器引擎秀仲,基于 Go 語言 并遵從Apache2.0協(xié)議開源鞋诗。
Docker 可以讓開發(fā)者打包他們的應(yīng)用以及依賴包到一個(gè)輕量級(jí)、可移植的容器中孤页,然后發(fā)布到任何流行的 Linux 機(jī)器上望薄,也可以實(shí)現(xiàn)虛擬化。
容器是完全使用沙箱機(jī)制,相互之間不會(huì)有任何接口(類似 iPhone 的 app),更重要的是容器性能開銷極低。
為什么用docker
簡(jiǎn)化程序:
Docker 讓開發(fā)者可以打包他們的應(yīng)用以及依賴包到一個(gè)可移植的容器中撞蜂,然后發(fā)布到任何流行的 Linux 機(jī)器上,便可以實(shí)現(xiàn)虛擬化智末。Docker改變了虛擬化的方式谅摄,使開發(fā)者可以直接將自己的成果放入Docker中進(jìn)行管理徒河。方便快捷已經(jīng)是 Docker的最大優(yōu)勢(shì)系馆,過去需要用數(shù)天乃至數(shù)周的 任務(wù),在Docker容器的處理下顽照,只需要數(shù)秒就能完成由蘑。
避免選擇恐懼癥:如果你有選擇恐懼癥,還是資深患者代兵。Docker 幫你 打包你的糾結(jié)尼酿!比如 Docker 鏡像;Docker 鏡像中包含了運(yùn)行環(huán)境和配置植影,所以 Docker 可以簡(jiǎn)化部署多種應(yīng)用實(shí)例工作裳擎。比如 Web 應(yīng)用、后臺(tái)應(yīng)用思币、數(shù)據(jù)庫(kù)應(yīng)用鹿响、大數(shù)據(jù)應(yīng)用比如 Hadoop 集群、消息隊(duì)列等等都可以打包成一個(gè)鏡像部署谷饿。
節(jié)省開支一方面惶我,云計(jì)算時(shí)代到來,使開發(fā)者不必為了追求效果而配置高額的硬件博投,Docker 改變了高性能必然高價(jià)格的思維定勢(shì)绸贡。Docker 與云的結(jié)合,讓云空間得到更充分的利用毅哗。不僅解決了硬件管理的問題听怕,也改變了虛擬化的方式。
持續(xù)交付和部署
對(duì)開發(fā)和運(yùn)維(DevOps)人員來說虑绵,最希望的就是一次創(chuàng)建或配置叉跛,可以在任意地方正常運(yùn)行。使用 Docker 可以通過定制應(yīng)用鏡像來實(shí)現(xiàn)持續(xù)集成蒸殿、持續(xù)交付筷厘、部署鸣峭。開發(fā)人員可以通過 Dockerfile 來進(jìn)行鏡像構(gòu)建,并結(jié)合 持續(xù)集成(Continuous Integration) 系統(tǒng)進(jìn)行集成測(cè)試酥艳,而運(yùn)維人員則可以直接在生產(chǎn)環(huán)境中快速部署該鏡像摊溶,甚至結(jié)合 持續(xù)部署(Continuous Delivery/Deployment) 系統(tǒng)進(jìn)行自動(dòng)部署。而且使用 Dockerfile 使鏡像構(gòu)建透明化充石,不僅僅開發(fā)團(tuán)隊(duì)可以理解應(yīng)用運(yùn)行環(huán)境莫换,也方便運(yùn)維團(tuán)隊(duì)理解應(yīng)用運(yùn)行所需條件,幫助更好的生產(chǎn)環(huán)境中部署該鏡像
更輕松的遷移
由于 Docker 確保了執(zhí)行環(huán)境的一致性骤铃,使得應(yīng)用的遷移更加容易拉岁。Docker 可以在很多平臺(tái)上運(yùn)行,無論是物理機(jī)惰爬、虛擬機(jī)喊暖、公有云、私有云撕瞧,甚至是筆記本陵叽,其運(yùn)行結(jié)果是一致的。因此用戶可以很輕易的將在一個(gè)平臺(tái)上運(yùn)行的應(yīng)用丛版,遷移到另一個(gè)平臺(tái)上巩掺,而不用擔(dān)心運(yùn)行環(huán)境的變化導(dǎo)致應(yīng)用無法正常運(yùn)行的情況
對(duì)比傳統(tǒng)虛擬機(jī)總結(jié)
Docker總結(jié)
Docker是世界領(lǐng)先的軟件容器平臺(tái)。
Docker使用Google公司推出的Go語言進(jìn)行開發(fā)實(shí)現(xiàn)页畦,基于Linux內(nèi)核的cgroup胖替,namespace,以及AUFS類的UnionFS等技術(shù)豫缨,對(duì)進(jìn)程進(jìn)行封裝隔離独令,屬于操作系統(tǒng)層面的虛擬化技術(shù)。由于隔離的進(jìn)程獨(dú)立于宿主和其它的隔離的進(jìn)程州胳,因此也稱其為容器记焊。Docke最初實(shí)現(xiàn)是基于LXC。
Docker能夠自動(dòng)執(zhí)行重復(fù)性任務(wù)栓撞,例如搭建和配置開發(fā)環(huán)境遍膜,從而解放了開發(fā)人員以便他們專注在真正重要的事情上:構(gòu)建杰出的軟件。
用戶可以方便地創(chuàng)建和使用容器瓤湘,把自己的應(yīng)用放入容器瓢颅。容器還可以進(jìn)行版本管理、復(fù)制弛说、分享挽懦、修改,就像管理普通的代碼一樣木人。
Docker的鏡像提供了除內(nèi)核外完整的運(yùn)行時(shí)環(huán)境信柿,確保了應(yīng)用運(yùn)行環(huán)境一致性冀偶,從而不會(huì)再出現(xiàn)“這段代碼在我機(jī)器上沒問題啊”這類問題;——一致的運(yùn)行環(huán)境
可以做到秒級(jí)渔嚷、甚至毫秒級(jí)的啟動(dòng)時(shí)間进鸠。大大的節(jié)約了開發(fā)、測(cè)試形病、部署的時(shí)間客年。——更快速的啟動(dòng)時(shí)間
避免公用的服務(wù)器漠吻,資源會(huì)容易受到其他用戶的影響量瓜。——隔離性
善于處理集中爆發(fā)的服務(wù)器使用壓力途乃;——彈性伸縮绍傲,快速擴(kuò)展
可以很輕易的將在一個(gè)平臺(tái)上運(yùn)行的應(yīng)用,遷移到另一個(gè)平臺(tái)上欺劳,而不用擔(dān)心運(yùn)行環(huán)境的變化導(dǎo)致應(yīng)用無法正常運(yùn)行的情況唧取∏穑——遷移方便
使用Docker可以通過定制應(yīng)用鏡像來實(shí)現(xiàn)持續(xù)集成划提、持續(xù)交付、部署邢享∨敉——持續(xù)交付和部署
Docker架構(gòu)
Docker 使用客戶端-服務(wù)器 (C/S) 架構(gòu)模式,使用遠(yuǎn)程API來管理和創(chuàng)建Docker容器骇塘。
Docker 容器通過 Docker 鏡像來創(chuàng)建伊履。
容器與鏡像的關(guān)系類似于面向?qū)ο缶幊讨械膶?duì)象與類
Docker 基本概念
Docker 包括三個(gè)基本概念
鏡像(Image)
容器(Container)
倉(cāng)庫(kù)(Repository)
理解了這三個(gè)概念,就理解了 Docker 的整個(gè)生命周期款违。
Docker 引擎
Docker 架構(gòu)
Docker 使用客戶端-服務(wù)器 (C/S) 架構(gòu)模式唐瀑,使用遠(yuǎn)程API來管理和創(chuàng)建Docker容器。
Docker 容器通過 Docker 鏡像來創(chuàng)建插爹。
容器與鏡像的關(guān)系類似于面向?qū)ο缶幊讨械膶?duì)象與類哄辣。
Docker 鏡像
Docker 鏡像是一個(gè)特殊的文件系統(tǒng),除了提供容器運(yùn)行時(shí)所需的程序赠尾、庫(kù)力穗、資源、配置等文件外气嫁,還包含了一些為運(yùn)行時(shí)準(zhǔn)備的一些配置參數(shù)(如匿名卷当窗、環(huán)境變量、用戶等)寸宵。鏡像不包含任何動(dòng)態(tài)數(shù)據(jù)崖面,其內(nèi)容在構(gòu)建之后也不會(huì)被改變元咙。
分層存儲(chǔ)
因?yàn)殓R像包含操作系統(tǒng)完整的 root 文件系統(tǒng),其體積往往是龐大的巫员,因此在 Docker 設(shè)計(jì)時(shí)蛾坯,就充分利用 Union FS 的技術(shù),將其設(shè)計(jì)為分層存儲(chǔ)的架構(gòu)疏遏。所以嚴(yán)格來說脉课,鏡像并非是像一個(gè) ISO 那樣的打包文件,鏡像只是一個(gè)虛擬的概念财异,其實(shí)際體現(xiàn)并非由一個(gè)文件組成倘零,而是由一組文件系統(tǒng)組成,或者說戳寸,由多層文件系統(tǒng)聯(lián)合組成呈驶。
鏡像構(gòu)建時(shí),會(huì)一層層構(gòu)建疫鹊,前一層是后一層的基礎(chǔ)袖瞻。每一層構(gòu)建完就不會(huì)再發(fā)生改變,后一層上的任何改變只發(fā)生在自己這一層拆吆。比如聋迎,刪除前一層文件的操作,實(shí)際不是真的刪除前一層的文件枣耀,而是僅在當(dāng)前層標(biāo)記為該文件已刪除霉晕。在最終容器運(yùn)行的時(shí)候,雖然不會(huì)看到這個(gè)文件捞奕,但是實(shí)際上該文件會(huì)一直跟隨鏡像牺堰。因此,在構(gòu)建鏡像的時(shí)候颅围,需要額外小心伟葫,每一層盡量只包含該層需要添加的東西,任何額外的東西應(yīng)該在該層構(gòu)建結(jié)束前清理掉院促。
分層存儲(chǔ)的特征還使得鏡像的復(fù)用筏养、定制變的更為容易。甚至可以用之前構(gòu)建好的鏡像作為基礎(chǔ)層一疯,然后進(jìn)一步添加新的層撼玄,以定制自己所需的內(nèi)容,構(gòu)建新的鏡像墩邀。
java
Centos(linux)
docker
Docker 容器
容器與鏡像的關(guān)系類似于面向?qū)ο缶幊讨械膶?duì)象與類掌猛。
鏡像(Image)和容器(Container)的關(guān)系,就像是面向?qū)ο蟪绦蛟O(shè)計(jì)中的 類 和 實(shí)例 一樣,鏡像是靜態(tài)的定義荔茬,容器是鏡像運(yùn)行時(shí)的實(shí)體废膘。容器可以被創(chuàng)建、啟動(dòng)慕蔚、停止丐黄、刪除、暫停等孔飒。
容器的實(shí)質(zhì)是進(jìn)程灌闺,但與直接在宿主執(zhí)行的進(jìn)程不同,容器進(jìn)程運(yùn)行于屬于自己的獨(dú)立的 命名空間坏瞄。因此容器可以擁有自己的 root 文件系統(tǒng)桂对、自己的網(wǎng)絡(luò)配置、自己的進(jìn)程空間鸠匀,甚至自己的用戶 ID 空間蕉斜。容器內(nèi)的進(jìn)程是運(yùn)行在一個(gè)隔離的環(huán)境里,使用起來缀棍,就好像是在一個(gè)獨(dú)立于宿主的系統(tǒng)下操作一樣宅此。這種特性使得容器封裝的應(yīng)用比直接在宿主運(yùn)行更加安全。也因?yàn)檫@種隔離的特性爬范,很多人初學(xué) Docker 時(shí)常常會(huì)混淆容器和虛擬機(jī)父腕。
前面講過鏡像使用的是分層存儲(chǔ),容器也是如此坦敌。每一個(gè)容器運(yùn)行時(shí)侣诵,是以鏡像為基礎(chǔ)層痢法,在其上創(chuàng)建一個(gè)當(dāng)前容器的存儲(chǔ)層狱窘,我們可以稱這個(gè)為容器運(yùn)行時(shí)讀寫而準(zhǔn)備的存儲(chǔ)層為容器存儲(chǔ)層。
容器存儲(chǔ)層的生存周期和容器一樣财搁,容器消亡時(shí)蘸炸,容器存儲(chǔ)層也隨之消亡。因此尖奔,任何保存于容器存儲(chǔ)層的信息都會(huì)隨容器刪除而丟失搭儒。
按照 Docker 最佳實(shí)踐的要求,容器不應(yīng)該向其存儲(chǔ)層內(nèi)寫入任何數(shù)據(jù)提茁,容器存儲(chǔ)層要保持無狀態(tài)化淹禾。所有的文件寫入操作,都應(yīng)該使用 數(shù)據(jù)卷(Volume)茴扁、或者綁定宿主目錄铃岔,在這些位置的讀寫會(huì)跳過容器存儲(chǔ)層,直接對(duì)宿主(或網(wǎng)絡(luò)存儲(chǔ))發(fā)生讀寫峭火,其性能和穩(wěn)定性更高毁习。
數(shù)據(jù)卷的生存周期獨(dú)立于容器智嚷,容器消亡,數(shù)據(jù)卷不會(huì)消亡纺且。因此盏道,使用數(shù)據(jù)卷后,容器刪除或者重新運(yùn)行之后载碌,數(shù)據(jù)卻不會(huì)丟失
Docker 倉(cāng)庫(kù)
Docker 倉(cāng)庫(kù)用來保存鏡像猜嘱,可以理解為代碼控制中的代碼倉(cāng)庫(kù)。
Docker Hub(https://hub.docker.com) 提供了龐大的鏡像集合供使用嫁艇。
公有 Docker Registry
Docker Registry 公開服務(wù)是開放給用戶使用泉坐、允許用戶管理鏡像的 Registry 服務(wù)。一般這類公開服務(wù)允許用戶免費(fèi)上傳裳仆、下載公開的鏡像腕让,并可能提供收費(fèi)服務(wù)供用戶管理私有鏡像。
最常使用的 Registry 公開服務(wù)是官方的 Docker Hub歧斟,這也是默認(rèn)的 Registry纯丸,并擁有大量的高質(zhì)量的官方鏡像。除此以外静袖,還有 CoreOS 的 Quay.io觉鼻,CoreOS 相關(guān)的鏡像存儲(chǔ)在這里;Google 的 Google Container Registry队橙,Kubernetes 的鏡像使用的就是這個(gè)服務(wù)。
由于某些原因捐康,在國(guó)內(nèi)訪問這些服務(wù)可能會(huì)比較慢仇矾。國(guó)內(nèi)的一些云服務(wù)商提供了針對(duì) Docker Hub 的鏡像服務(wù)(Registry Mirror),這些鏡像服務(wù)被稱為加速器解总。常見的有 阿里云加速器贮匕、DaoCloud 加速器 等。使用加速器會(huì)直接從國(guó)內(nèi)的地址下載 Docker Hub 的鏡像花枫,比直接從 Docker Hub 下載速度會(huì)提高很多刻盐。
國(guó)內(nèi)也有一些云服務(wù)商提供類似于 Docker Hub 的公開服務(wù)。比如 時(shí)速云鏡像倉(cāng)庫(kù)劳翰、網(wǎng)易云鏡像服務(wù)敦锌、DaoCloud 鏡像市場(chǎng)、阿里云鏡像庫(kù) 等佳簸。
私有 Docker Registry
除了使用公開服務(wù)外乙墙,用戶還可以在本地搭建私有 Docker Registry。Docker 官方提供了 Docker Registry 鏡像,可以直接使用做為私有 Registry 服務(wù)伶丐。
開源的 Docker Registry 鏡像只提供了 Docker Registry API 的服務(wù)端實(shí)現(xiàn)悼做,足以支持 docker 命令,不影響使用哗魂。但不包含圖形界面肛走,以及鏡像維護(hù)、用戶管理录别、訪問控制等高級(jí)功能朽色。在官方的商業(yè)化版本 Docker Trusted Registry 中,提供了這些高級(jí)功能组题。
除了官方的 Docker Registry 外葫男,還有第三方軟件實(shí)現(xiàn)了 Docker Registry API,甚至提供了用戶界面以及一些高級(jí)功能崔列。比如梢褐,VMWare Harbor 和 Sonatype Nexus。
Docker安裝
CentOS安裝要求:
http://www.runoob.com/docker/centos-docker-install.html
Docker支持以下的CentOS版本:
CentOS 7 (64-bit)
CentOS 6.5 (64-bit) 或更高的版本
安裝
目前赵讯,CentOS 僅發(fā)行版本中的內(nèi)核支持 Docker盈咳。
Docker 運(yùn)行在 CentOS 7 上,要求系統(tǒng)為64位边翼、系統(tǒng)內(nèi)核版本為 3.10 以上鱼响。
Docker 運(yùn)行在 CentOS-6.5 或更高的版本的 CentOS 上,要求系統(tǒng)為64位组底、系統(tǒng)內(nèi)核版本為 2.6.32-431 或者更高版本
1丈积、校驗(yàn)版本
命令:uname -r
3.10以上版本
校驗(yàn)Linux內(nèi)核版本
從 2017 年 3 月開始 docker 在原來的基礎(chǔ)上分為兩個(gè)分支版本: Docker CE 和 Docker EE。
Docker CE 即社區(qū)免費(fèi)版债鸡,Docker EE 即企業(yè)版江滨,強(qiáng)調(diào)安全,但需付費(fèi)使用娘锁。
本文介紹 Docker CE 的安裝使用牙寞。
2、移除舊的版本
sudo yum remove docker \
docker-client \
docker-client-latest \
docker-common \
docker-latest \
docker-latest-logrotate \
docker-logrotate \
docker-selinux \
docker-engine-selinux \
docker-engine
3莫秆、安裝一些必要的系統(tǒng)工具:
sudo yum install -y yum-utils device-mapper-persistent-data lvm2
4峭范、添加軟件源信息(不建議用aliyun源 docker-compose可能會(huì)因?yàn)樵窗惭b不上):
sudo yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
5薄啥、更新 yum 緩存:
sudo yum makecache fast
6、安裝 Docker-ce:
sudo yum -y install docker-ce
7蒲凶、啟動(dòng) Docker 后臺(tái)服務(wù):
sudo systemctl start docker
8茄螃、重啟 Docker服務(wù):
sudo systemctl restart docker
安裝成功后可通過:
docker version
刪除
執(zhí)行以下命令來刪除 Docker CE:
$ sudo yum remove docker-ce
$ sudo rm -rf /var/lib/docker
Docker 鏡像加速器
鑒于國(guó)內(nèi)網(wǎng)絡(luò)問題缝驳,后續(xù)拉取 Docker 鏡像十分緩慢,我們可以需要配置加速器來解決
Docker 官方和國(guó)內(nèi)很多云服務(wù)商都提供了國(guó)內(nèi)加速器服務(wù),例如:
Docker 官方提供的中國(guó) registry mirror
阿里云加速器
DaoCloud 加速器
我們以 Docker 官方加速器為例進(jìn)行介紹
https://docs.docker.com/registry/recipes/mirror/#use-case-the-china-registry-mirror
CentOS 7
通過命令查看:在 /etc/docker/daemon.json 中寫入如下內(nèi)容(如果文件不存在請(qǐng)新建該文件)
{
"registry-mirrors": ["https://registry.docker-cn.com"]
}
注意用狱,一定要保證該文件符合 json 規(guī)范运怖,否則 Docker 將不能啟動(dòng)
重啟Docker:
sudo systemctl daemon-reload
sudo systemctl restart docker
檢查加速器是否生效
配置加速器之后,如果拉取鏡像仍然十分緩慢夏伊,請(qǐng)手動(dòng)檢查加速器配置是否生效摇展,在命令行執(zhí)行 docker info,如果從結(jié)果中看到了如下內(nèi)容溺忧,說明配置成功
測(cè)試
嘗試從docker庫(kù)中下載鏡像:
docker pull tomcat
通過觀察咏连,下載速度明顯提升。
查看docker下載的鏡像內(nèi)容:
docker images
下載指定的鏡像版本:
docker images tomcat:9-jre11
啟動(dòng)tomcat:
docker run –p 8080:8080 tomcat
Docker鏡像
鏡像是Docker的三大組件之一鲁森。
Docker運(yùn)行容器前需要本地存在對(duì)應(yīng)的鏡像祟滴,如果本地不存,Docker會(huì)從鏡像倉(cāng)庫(kù)下載歌溉。
本節(jié)將介紹更多關(guān)于鏡像的內(nèi)容垄懂,包括:
從倉(cāng)庫(kù)獲取鏡像;
管理本地主機(jī)上的鏡像痛垛;
介紹鏡像實(shí)現(xiàn)的基本原理;
Docker 獲取鏡像
之前提到過埠偿,Docker Hub 上有大量的高質(zhì)量的鏡像可以用,這里我們就說一下怎么獲取這些鏡像榜晦。
從 Docker 鏡像倉(cāng)庫(kù)獲取鏡像的命令是 docker pull冠蒋。其命令格式為:
具體的選項(xiàng)可以通過 docker pull --help 命令看到,這里我們說一下鏡像名稱的格式乾胶。
Docker 鏡像倉(cāng)庫(kù)地址:地址的格式一般是 <域名/IP>[:端口號(hào)]抖剿。默認(rèn)地址是 Docker Hub。
倉(cāng)庫(kù)名:如之前所說识窿,這里的倉(cāng)庫(kù)名是兩段式名稱斩郎,即 <用戶名>/<軟件名>。對(duì)于 Docker Hub喻频,如果不給出用戶名缩宜,則默認(rèn)為 library,也就是官方鏡像甥温。
示例:
上面的命令中沒有給出 Docker 鏡像倉(cāng)庫(kù)地址锻煌,因此將會(huì)從 Docker Hub 獲取鏡像。而鏡像名稱是 centos:7.1.1503姻蚓,因此將會(huì)獲取官方鏡像 library/centos倉(cāng)庫(kù)中標(biāo)簽為 7.1.1503 的鏡像宋梧。
從下載過程中可以看到我們之前提及的分層存儲(chǔ)的概念,鏡像是由多層存儲(chǔ)所構(gòu)成狰挡。下載也是一層層的去下載捂龄,并非單一文件释涛。下載過程中給出了每一層的 ID 的前 12 位。并且下載結(jié)束后倦沧,給出該鏡像完整的 sha256 的摘要唇撬,以確保下載一致性。
在使用上面命令的時(shí)候展融,你可能會(huì)發(fā)現(xiàn)窖认,你所看到的層 ID 以及 sha256 的摘要和這里的不一樣。這是因?yàn)楣俜界R像是一直在維護(hù)的愈污,有任何新的 bug耀态,或者版本更新,都會(huì)進(jìn)行修復(fù)再以原來的標(biāo)簽發(fā)布暂雹,這樣可以確保任何使用這個(gè)標(biāo)簽的用戶可以獲得更安全首装、更穩(wěn)定的鏡像。
運(yùn)行
有了鏡像后杭跪,我們就能夠以這個(gè)鏡像為基礎(chǔ)啟動(dòng)并運(yùn)行一個(gè)容器仙逻。以上面的 centos:7.1.1503 為例,如果我們打算啟動(dòng)里面的 bash 并且進(jìn)行交互式操作的話涧尿,可以執(zhí)行下面的命令
docker run 就是運(yùn)行容器的命令系奉,我們這里簡(jiǎn)要的說明一下上面用到的參數(shù)。
-it:這是兩個(gè)參數(shù)姑廉,一個(gè)是 -i:交互式操作缺亮,一個(gè)是 -t 終端。這里打算進(jìn)入 bash 執(zhí)行一些命令并查看返回結(jié)果桥言,因此我們需要交互式終端萌踱。
--rm:這個(gè)參數(shù)是說容器退出后隨之將其刪除。默認(rèn)情況下号阿,為了排障需求并鸵,退出的容器并不會(huì)立即刪除,除非手動(dòng) docker rm扔涧。我們這里只是隨便執(zhí)行個(gè)命令园担,看看結(jié)果,不需要排障和保留結(jié)果枯夜,因此使用 --rm 可以避免浪費(fèi)空間弯汰。(可通過新開一窗口docker ps –a 查看)
centos:7.1.1503:這是指用 centos:7.1.1503 鏡像為基礎(chǔ)來啟動(dòng)容器。
bash:放在鏡像名后的是命令卤档,這里我們希望有個(gè)交互式 Shell蝙泼,因此用的是 bash。
進(jìn)入容器后劝枣,我們可以在 Shell 下操作汤踏,執(zhí)行任何所需的命令。這里舔腾,我們執(zhí)行了 cat /etc/os-release溪胶,這是 Linux 常用的查看當(dāng)前系統(tǒng)版本的命令,從返回的結(jié)果可以看到容器內(nèi)是 centos:7系統(tǒng)稳诚。
最后我們通過 exit 退出了這個(gè)容器哗脖。(Ctrl+D)
例:如果不使用 --rm 參數(shù),我們通過 docker ps –a 命令可看到:(容器退出后未刪除)扳还〔疟埽可通過 docker rm CONTAINER-ID 刪除
查找鏡像
我們可以從 Docker Hub 網(wǎng)站來搜索鏡像,Docker Hub 網(wǎng)址為: https://hub.docker.com/
我們也可以使用 docker search 命令來搜索鏡像氨距。比如我們需要一個(gè)httpd的鏡像來作為我們的web服務(wù)桑逝。我們可以通過 docker search 命令搜索 httpd 來尋找適合我們的鏡像。
docker search httpd
Docker 列出鏡像
要想列出已經(jīng)下載下來的鏡像俏让,可以使用 docker image ls 命令楞遏。
列表包含了 倉(cāng)庫(kù)名、標(biāo)簽首昔、鏡像 ID寡喝、創(chuàng)建時(shí)間 以及 所占用的空間。
其中倉(cāng)庫(kù)名勒奇、標(biāo)簽在之前的基礎(chǔ)概念章節(jié)已經(jīng)介紹過了预鬓。鏡像 ID 則是鏡像的唯一標(biāo)識(shí),一個(gè)鏡像可以對(duì)應(yīng)多個(gè)標(biāo)簽赊颠。因此格二,如果擁有相同的 ID,因?yàn)樗鼈儗?duì)應(yīng)的是同一個(gè)鏡像巨税。
鏡像體積
如果仔細(xì)觀察蟋定,會(huì)注意到,這里標(biāo)識(shí)的所占用空間和在 Docker Hub 上看到的鏡像大小不同草添。這是因?yàn)?Docker Hub 中顯示的體積是壓縮后的體積驶兜。在鏡像下載和上傳過程中鏡像是保持著壓縮狀態(tài)的,因此 Docker Hub 所顯示的大小是網(wǎng)絡(luò)傳輸中更關(guān)心的流量大小远寸。而 docker image ls 顯示的是鏡像下載到本地后抄淑,展開的大小,準(zhǔn)確說驰后,是展開后的各層所占空間的總和肆资,因?yàn)殓R像到本地后,查看空間的時(shí)候灶芝,更關(guān)心的是本地磁盤空間占用的大小郑原。
另外一個(gè)需要注意的問題是唉韭,docker image ls 列表中的鏡像體積總和并非是所有鏡像實(shí)際硬盤消耗。由于 Docker 鏡像是多層存儲(chǔ)結(jié)構(gòu)犯犁,并且可以繼承属愤、復(fù)用,因此不同鏡像可能會(huì)因?yàn)槭褂孟嗤幕A(chǔ)鏡像酸役,從而擁有共同的層住诸。由于 Docker 使用 Union FS,相同的層只需要保存一份即可涣澡,因此實(shí)際鏡像硬盤占用空間很可能要比這個(gè)列表鏡像大小的總和要小的多贱呐。
虛懸鏡像
鏡像列表中,還可以看到一個(gè)特殊的鏡像入桂,這個(gè)鏡像既沒有倉(cāng)庫(kù)名奄薇,也沒有標(biāo)簽,均為 <none>
這個(gè)鏡像原本是有鏡像名和標(biāo)簽的事格,原來為 mongo:3.2惕艳,隨著官方鏡像維護(hù),發(fā)布了新版本后驹愚,重新 docker pull mongo:3.2 時(shí)远搪,mongo:3.2 這個(gè)鏡像名被轉(zhuǎn)移到了新下載的鏡像身上,而舊的鏡像上的這個(gè)名稱則被取消逢捺,從而成為了 <none>谁鳍。除了 docker pull 可能導(dǎo)致這種情況,docker build 也同樣可以導(dǎo)致這種現(xiàn)象劫瞳。由于新舊鏡像同名倘潜,舊鏡像名稱被取消,從而出現(xiàn)倉(cāng)庫(kù)名志于、標(biāo)簽均為 <none> 的鏡像涮因。這類無標(biāo)簽鏡像也被稱為 虛懸鏡像(dangling image) 。
一般來說伺绽,虛懸鏡像已經(jīng)失去了存在的價(jià)值养泡,是可以隨意刪除的,可以用下面的命令刪除:
Docker 刪除本地鏡像
如果要?jiǎng)h除本地的鏡像奈应,可以使用 docker image rmi 命令澜掩,
用 ID、鏡像名杖挣、摘要?jiǎng)h除鏡像
其中肩榕,<鏡像> 可以是 鏡像短 ID、鏡像長(zhǎng) ID惩妇、鏡像名 或者 鏡像摘要株汉。
練習(xí):
一筐乳、從docker官網(wǎng)上下載一個(gè)tomcat下來,啟動(dòng)并訪問郎逃。再將其鏡像移除哥童。
Docker pull tomcat
Docker run –it –rm –p 8080:8080 tomcat
Docker rm shaid
二挺份、對(duì)指定的容器進(jìn)行修改褒翰。將tomcat鏡像 的容器 主頁面進(jìn)行修改內(nèi)容
1、首先啟動(dòng)tomcat容器
docker run -it -p 8080:8080 tomcat
2匀泊、交互的方式進(jìn)入容器(修改指定頁面)
docker exec -it 7bfbdc2d10e4 bash
3优训、將主頁面index.jsp后追加
docker run //交互的方式啟動(dòng)容器
docker exec //交互的方式進(jìn)入容器
4、再訪問主頁面查看:
三各聘、將容器關(guān)閉后揣非,再訪問index.jsp。發(fā)現(xiàn)又變成新的原始內(nèi)容了
docker stop 9be696a0c283 //停止正運(yùn)行容器(或Ctrl+c)
Docker定制鏡像
當(dāng)我們從docker鏡像倉(cāng)庫(kù)中下載的鏡像不能滿足我們的需求時(shí)躲因,我們可以通過以下兩種方式對(duì)鏡像進(jìn)行更改早敬。
1.從已經(jīng)創(chuàng)建的容器中更新鏡像,并且提交這個(gè)鏡像
2.使用 Dockerfile 指令來創(chuàng)建一個(gè)新的鏡像
Dockerfile 定制鏡像
鏡像的定制實(shí)際上就是定制每一層所添加的配置大脉、文件搞监。如果我們可以把每一層修改、安裝镰矿、構(gòu)建琐驴、操作的命令都寫入一個(gè)腳本,用這個(gè)腳本來構(gòu)建秤标、定制鏡像绝淡,那么之前提及的無法重復(fù)的問題、鏡像構(gòu)建透明性的問題苍姜、體積的問題就都會(huì)解決牢酵。這個(gè)腳本就是 Dockerfile。
Dockerfile 是一個(gè)文本文件衙猪,其內(nèi)包含了一條條的指令(Instruction)馍乙,每一條指令構(gòu)建一層,因此每一條指令的內(nèi)容屈嗤,就是描述該層應(yīng)當(dāng)如何構(gòu)建潘拨。
還以之前定制 tomcat鏡像為例,這次我們使用 Dockerfile 來定制
案例:創(chuàng)建一個(gè)鏡像(基于tomcat) 里面要有一個(gè)index.html饶号,并寫入Hello qfjy Docker
在一個(gè)空白目錄中铁追,建立一個(gè)文本文件,并命名為 Dockerfile:
其內(nèi)容為:
這個(gè) Dockerfile 很簡(jiǎn)單茫船,一共就兩行琅束。涉及到了兩條指令扭屁,F(xiàn)ROM 和 RUN。
FROM 指定基礎(chǔ)鏡像
所謂定制鏡像涩禀,那一定是以一個(gè)鏡像為基礎(chǔ)料滥,在其上進(jìn)行定制。就像我們之前運(yùn)行了一個(gè) nginx 鏡像的容器艾船,再進(jìn)行修改一樣葵腹,基礎(chǔ)鏡像是必須指定的。而 FROM 就是指定基礎(chǔ)鏡像屿岂,因此一個(gè) Dockerfile中 FROM 是必備的指令践宴,并且必須是第一條指令。
在 Docker Store 上有非常多的高質(zhì)量的官方鏡像爷怀,有可以直接拿來使用的服務(wù)類的鏡像阻肩,如 nginx、redis运授、mongo烤惊、mysql、httpd吁朦、php柒室、tomcat 等;也有一些方便開發(fā)喇完、構(gòu)建伦泥、運(yùn)行各種語言應(yīng)用的鏡像,如 node锦溪、openjdk不脯、python、ruby刻诊、golang 等防楷。可以在其中尋找一個(gè)最符合我們最終目標(biāo)的鏡像為基礎(chǔ)鏡像進(jìn)行定制则涯。
如果沒有找到對(duì)應(yīng)服務(wù)的鏡像复局,官方鏡像中還提供了一些更為基礎(chǔ)的操作系統(tǒng)鏡像,如 ubuntu粟判、debian亿昏、centos、fedora档礁、alpine 等角钩,這些操作系統(tǒng)的軟件庫(kù)為我們提供了更廣闊的擴(kuò)展空間。
除了選擇現(xiàn)有鏡像為基礎(chǔ)鏡像外,Docker 還存在一個(gè)特殊的鏡像递礼,名為 scratch惨险。這個(gè)鏡像是虛擬的概念,并不實(shí)際存在脊髓,它表示一個(gè)空白的鏡像辫愉。
如果你以 scratch 為基礎(chǔ)鏡像的話,意味著你不以任何鏡像為基礎(chǔ)将硝,接下來所寫的指令將作為鏡像第一層開始存在恭朗。
不以任何系統(tǒng)為基礎(chǔ),直接將可執(zhí)行文件復(fù)制進(jìn)鏡像的做法并不罕見袋哼,比如 swarm冀墨、coreos/etcd。對(duì)于 Linux 下靜態(tài)編譯的程序來說涛贯,并不需要有操作系統(tǒng)提供運(yùn)行時(shí)支持,所需的一切庫(kù)都已經(jīng)在可執(zhí)行文件里了蔚出,因此直接 FROM scratch 會(huì)讓鏡像體積更加小巧弟翘。使用 Go 語言 開發(fā)的應(yīng)用很多會(huì)使用這種方式來制作鏡像,這也是為什么有人認(rèn)為 Go 是特別適合容器微服務(wù)架構(gòu)的語言的原因之一骄酗。
RUN 執(zhí)行命令
RUN 指令是用來執(zhí)行命令行命令的稀余。由于命令行的強(qiáng)大能力,RUN 指令在定制鏡像時(shí)是最常用的指令之一趋翻。其格式有兩種:
shell 格式:RUN <命令>睛琳,就像直接在命令行中輸入的命令一樣。剛才寫的 Dockerfile 中的 RUN 指令就是這種格式踏烙。
exec 格式:RUN ["可執(zhí)行文件", "參數(shù)1", "參數(shù)2"]师骗,這更像是函數(shù)調(diào)用中的格式。
既然 RUN 就像 Shell 腳本一樣可以執(zhí)行命令讨惩,那么我們是否就可以像 Shell 腳本一樣把每個(gè)命令對(duì)應(yīng)一個(gè) RUN 呢辟癌?比如這樣:
之前說過,Dockerfile 中每一個(gè)指令都會(huì)建立一層荐捻,RUN 也不例外黍少。每一個(gè) RUN 的行為,就和剛才我們手工建立鏡像的過程一樣:新建立一層处面,在其上執(zhí)行這些命令厂置,執(zhí)行結(jié)束后,commit 這一層的修改魂角,構(gòu)成新的鏡像昵济。
而上面的這種寫法,創(chuàng)建了 7 層鏡像。這是完全沒有意義的砸紊,而且很多運(yùn)行時(shí)不需要的東西传于,都被裝進(jìn)了鏡像里,比如編譯環(huán)境醉顽、更新的軟件包等等沼溜。結(jié)果就是產(chǎn)生非常臃腫、非常多層的鏡像游添,不僅僅增加了構(gòu)建部署的時(shí)間系草,也很容易出錯(cuò)。 這是很多初學(xué) Docker 的人常犯的一個(gè)錯(cuò)誤唆涝。
Union FS 是有最大層數(shù)限制的找都,比如 AUFS,曾經(jīng)是最大不得超過 42 層廊酣,現(xiàn)在是不得超過 127 層能耻。上面的 Dockerfile 正確的寫法應(yīng)該是這樣:
首先,之前所有的命令只有一個(gè)目的亡驰,就是編譯晓猛、安裝 redis 可執(zhí)行文件。因此沒有必要建立很多層凡辱,這只是一層的事情戒职。因此,這里沒有使用很多個(gè) RUN 對(duì)一一對(duì)應(yīng)不同的命令透乾,而是僅僅使用一個(gè) RUN 指令洪燥,并使用 && 將各個(gè)所需命令串聯(lián)起來。將之前的 7 層乳乌,簡(jiǎn)化為了 1 層捧韵。在撰寫 Dockerfile 的時(shí)候,要經(jīng)常提醒自己钦扭,這并不是在寫 Shell 腳本纫版,而是在定義每一層該如何構(gòu)建。
并且客情,這里為了格式化還進(jìn)行了換行其弊。Dockerfile 支持 Shell 類的行尾添加 \ 的命令換行方式,以及行首 # 進(jìn)行注釋的格式膀斋。良好的格式梭伐,比如換行、縮進(jìn)仰担、注釋等糊识,會(huì)讓維護(hù)、排障更為容易,這是一個(gè)比較好的習(xí)慣赂苗。
此外愉耙,還可以看到這一組命令的最后添加了清理工作的命令,刪除了為了編譯構(gòu)建所需要的軟件拌滋,清理了所有下載朴沿、展開的文件,并且還清理了 apt 緩存文件败砂。這是很重要的一步赌渣,我們之前說過,鏡像是多層存儲(chǔ)昌犹,每一層的東西并不會(huì)在下一層被刪除坚芜,會(huì)一直跟隨著鏡像。因此鏡像構(gòu)建時(shí)斜姥,一定要確保每一層只添加真正需要添加的東西鸿竖,任何無關(guān)的東西都應(yīng)該清理掉。
很多人初學(xué) Docker 制作出了很臃腫的鏡像的原因之一疾渴,就是忘記了每一層構(gòu)建的最后一定要清理掉無關(guān)文件千贯。
build構(gòu)建鏡像
回到之前定制的 tomcat 鏡像的 Dockerfile 來。現(xiàn)在我們明白了這個(gè) Dockerfile 的內(nèi)容搞坝,那么讓我們來構(gòu)建這個(gè)鏡像吧。
在 Dockerfile 文件所在目錄執(zhí)行:
從命令的輸出結(jié)果中魁袜,我們可以清晰的看到鏡像的構(gòu)建過程桩撮。在 Step 2 中,如同我們之前所說的那樣峰弹,RUN 指令啟動(dòng)了一個(gè)容器 9f8…店量,執(zhí)行了所要求的命令,并最后提交了這一層 9f8..鞠呈,隨后刪除了所用到的這個(gè)容器 d93..融师。
這里我們使用了 docker build 命令進(jìn)行鏡像構(gòu)建。其格式為:
-t :指定要?jiǎng)?chuàng)建的目標(biāo)鏡像名
. :Dockerfile 文件所在目錄蚁吝,可以指定Dockerfile 的絕對(duì)路徑
在這里我們指定了最終鏡像的名稱 -t tomcat-1绵载,構(gòu)建成功后宣脉,我們可以像之前運(yùn)行 tomcat 那樣來運(yùn)行這個(gè)鏡像,其結(jié)果會(huì)和 tomcat 一樣。(如果有版本號(hào)名稱:tomcat:01)
案例:基于上一個(gè)鏡像(基于tomcat) 將ROOT內(nèi)多余的文件都刪除民鼓。只保留index.html
1、修改Dockerfile
構(gòu)建鏡像
docker build –t 鏡像名 .
查看鏡像列表 docker images
刪除虛擬鏡像
docker image prune
WORKDIR 指定工作目錄
格式為 WORKDIR <工作目錄路徑>润脸。
使用 WORKDIR 指令可以來指定工作目錄(或者稱為當(dāng)前目錄)怔球,以后各層的當(dāng)前目錄就被改為指定的目錄,如該目錄不存在,WORKDIR 會(huì)幫你建立目錄桑孩。
之前提到一些初學(xué)者常犯的錯(cuò)誤是把 Dockerfile 等同于 Shell 腳本來書寫拜鹤,這種錯(cuò)誤的理解還可能會(huì)導(dǎo)致出現(xiàn)下面這樣的錯(cuò)誤:
如果將這個(gè) Dockerfile 進(jìn)行構(gòu)建鏡像運(yùn)行后,會(huì)發(fā)現(xiàn)找不到 /use/local 文件流椒,或者其內(nèi)容不是想要的敏簿。原因其實(shí)很簡(jiǎn)單,在 Shell 中镣隶,連續(xù)兩行是同一個(gè)進(jìn)程執(zhí)行環(huán)境极谊,因此前一個(gè)命令修改的內(nèi)存狀態(tài),會(huì)直接影響后一個(gè)命令安岂;而在 Dockerfile 中轻猖,這兩行 RUN 命令的執(zhí)行環(huán)境根本不同,是兩個(gè)完全不同的容器域那。這就是對(duì) Dockerfile 構(gòu)建分層存儲(chǔ)的概念不了解所導(dǎo)致的錯(cuò)誤咙边。
之前說過每一個(gè) RUN 都是啟動(dòng)一個(gè)容器、執(zhí)行命令次员、然后提交存儲(chǔ)層文件變更败许。第一層 RUN cd /usr/local/tomcat的執(zhí)行僅僅是當(dāng)前進(jìn)程的工作目錄變更,一個(gè)內(nèi)存上的變化而已淑蔚,其結(jié)果不會(huì)造成任何文件變更市殷。而到第二層的時(shí)候,啟動(dòng)的是一個(gè)全新的容器刹衫,跟第一層的容器更完全沒關(guān)系醋寝,自然不可能繼承前一層構(gòu)建過程中的內(nèi)存變化。
因此如果需要改變以后各層的工作目錄的位置带迟,那么應(yīng)該使用 WORKDIR 指令音羞。
鏡像構(gòu)建上下文(Context)
如果注意,會(huì)看到 docker build 命令最后有一個(gè) .仓犬。. 表示當(dāng)前目錄嗅绰,而 Dockerfile 就在當(dāng)前目錄,因此不少初學(xué)者以為這個(gè)路徑是在指定 Dockerfile 所在路徑搀继,這么理解其實(shí)是不準(zhǔn)確的窘面。如果對(duì)應(yīng)上面的命令格式,你可能會(huì)發(fā)現(xiàn)律歼,這是在指定上下文路徑民镜。那么什么是上下文呢?
首先我們要理解 docker build 的工作原理险毁。Docker 在運(yùn)行時(shí)分為 Docker 引擎(也就是服務(wù)端守護(hù)進(jìn)程)和客戶端工具制圈。Docker 的引擎提供了一組 REST API们童,被稱為 Docker Remote API,而如 docker命令這樣的客戶端工具鲸鹦,則是通過這組 API 與 Docker 引擎交互慧库,從而完成各種功能。因此馋嗜,雖然表面上我們好像是在本機(jī)執(zhí)行各種 docker 功能齐板,但實(shí)際上,一切都是使用的遠(yuǎn)程調(diào)用形式在服務(wù)端(Docker 引擎)完成葛菇。也因?yàn)檫@種 C/S 設(shè)計(jì)甘磨,讓我們操作遠(yuǎn)程服務(wù)器的 Docker 引擎變得輕而易舉。
當(dāng)我們進(jìn)行鏡像構(gòu)建的時(shí)候眯停,并非所有定制都會(huì)通過 RUN 指令完成济舆,經(jīng)常會(huì)需要將一些本地文件復(fù)制進(jìn)鏡像,比如通過 COPY 指令莺债、ADD 指令等滋觉。而 docker build 命令構(gòu)建鏡像,其實(shí)并非在本地構(gòu)建齐邦,而是在服務(wù)端椎侠,也就是 Docker 引擎中構(gòu)建的。那么在這種客戶端/服務(wù)端的架構(gòu)中措拇,如何才能讓服務(wù)端獲得本地文件呢我纪?
這就引入了上下文的概念。當(dāng)構(gòu)建的時(shí)候丐吓,用戶會(huì)指定構(gòu)建鏡像上下文的路徑宣羊,docker build 命令得知這個(gè)路徑后,會(huì)將路徑下的所有內(nèi)容打包汰蜘,然后上傳給 Docker 引擎。這樣 Docker 引擎收到這個(gè)上下文包后之宿,展開就會(huì)獲得構(gòu)建鏡像所需的一切文件族操。
案例:基于上一個(gè)鏡像(基于tomcat) 外部復(fù)制一個(gè)文件(圖片),并復(fù)制下并能訪問
構(gòu)建境像:
docker build –t tomcat_1 .
運(yùn)行:
docker run -it --rm –d –p 8080:8080 tomcat_1
docker exec –it 容器id bash
COPY 復(fù)制文件
格式:
COPY <源路徑>... <目標(biāo)路徑>
COPY ["<源路徑1>",... "<目標(biāo)路徑>"]
和 RUN 指令一樣比被,也有兩種格式色难,一種類似于命令行,一種類似于函數(shù)調(diào)用等缀。
COPY 指令將從構(gòu)建上下文目錄中 <源路徑> 的文件/目錄復(fù)制到新的一層的鏡像內(nèi)的 <目標(biāo)路徑> 位置枷莉。比如:
COPY qfjy.png /usr/local/tomcat/webapps/ROOT/
<目標(biāo)路徑> 可以是容器內(nèi)的絕對(duì)路徑,也可以是相對(duì)于工作目錄的相對(duì)路徑(工作目錄可以用 WORKDIR指令來指定)尺迂。目標(biāo)路徑不需要事先創(chuàng)建笤妙,如果目錄不存在會(huì)在復(fù)制文件前先行創(chuàng)建缺失目錄冒掌。
此外,還需要注意一點(diǎn)蹲盘,使用 COPY 指令股毫,源文件的各種元數(shù)據(jù)都會(huì)保留。比如讀召衔、寫铃诬、執(zhí)行權(quán)限、文件變更時(shí)間等苍凛。這個(gè)特性對(duì)于鏡像定制很有用趣席。特別是構(gòu)建相關(guān)文件都在使用 Git 進(jìn)行管理的時(shí)候。
案例:部署項(xiàng)目到Docker容器(練習(xí))
1醇蝴、docker下創(chuàng)建項(xiàng)目工程名稱
mkdir -p /usr/local/docker/qfjy_exam
cd /usr/local/docker/qfjy_exam
2宣肚、將桌面qfjy_exam.zip復(fù)制到訪目錄下
cp qfjy_exam-1.0-SNAPSHOT.zip /usr/local/docker/qfjy_exam/
3、創(chuàng)建鏡像文件Dockerfile
4哑蔫、構(gòu)建鏡像
docker build -t qfjy_exam .
5钉寝、進(jìn)入鏡像內(nèi)查看:
docker run -it qfjy_exam bash
2步、將默認(rèn)端口號(hào)改為8081
EXPOSE 暴露端口
格式為 EXPOSE <端口1> [<端口2>...]闸迷。
EXPOSE 指令是聲明運(yùn)行時(shí)容器提供服務(wù)端口嵌纲,這只是一個(gè)聲明,在運(yùn)行時(shí)并不會(huì)因?yàn)檫@個(gè)聲明應(yīng)用就會(huì)開啟這個(gè)端口的服務(wù)腥沽。在 Dockerfile 中寫入這樣的聲明有兩個(gè)好處逮走,一個(gè)是幫助鏡像使用者理解這個(gè)鏡像服務(wù)的守護(hù)端口,以方便配置映射今阳;另一個(gè)用處則是在運(yùn)行時(shí)使用隨機(jī)端口映射時(shí)师溅,也就是 docker run -P 時(shí),會(huì)自動(dòng)隨機(jī)映射 EXPOSE 的端口盾舌。
此外墓臭,在早期 Docker 版本中還有一個(gè)特殊的用處。以前所有容器都運(yùn)行于默認(rèn)橋接網(wǎng)絡(luò)中妖谴,因此所有容器互相之間都可以直接訪問窿锉,這樣存在一定的安全性問題。于是有了一個(gè) Docker 引擎參數(shù) --icc=false膝舅,當(dāng)指定該參數(shù)后嗡载,容器間將默認(rèn)無法互訪,除非互相間使用了 --links 參數(shù)的容器才可以互通仍稀,并且只有鏡像中 EXPOSE 所聲明的端口才可以被訪問洼滚。這個(gè) --icc=false 的用法,在引入了 docker network 后已經(jīng)基本不用了技潘,通過自定義網(wǎng)絡(luò)可以很輕松的實(shí)現(xiàn)容器間的互聯(lián)與隔離遥巴。
要將 EXPOSE 和在運(yùn)行時(shí)使用 -p <宿主端口>:<容器端口> 區(qū)分開來千康。-p,是映射宿主端口和容器端口挪哄,換句話說吧秕,就是將容器的對(duì)應(yīng)端口服務(wù)公開給外界訪問,而 EXPOSE 僅僅是聲明容器打算使用什么端口而已迹炼,并不會(huì)自動(dòng)在宿主進(jìn)行端口映射
docker run -P 時(shí)砸彬,會(huì)自動(dòng)隨機(jī)映射 EXPOSE 的端口。
執(zhí)行 -P
docker run -P tomcat_1
瀏覽器訪問:
docker run -p 時(shí)斯入,<宿主端口>:<容器端口> (將容器的端口指定宿主機(jī)端口)
Docker 容器
容器是 Docker 又一核心概念砂碉。
簡(jiǎn)單的說,容器是獨(dú)立運(yùn)行的一個(gè)或一組應(yīng)用刻两,以及它們的運(yùn)行態(tài)環(huán)境增蹭。對(duì)應(yīng)的,虛擬機(jī)可以理解為模擬運(yùn)行的一整套操作系統(tǒng)(提供了運(yùn)行態(tài)環(huán)境和其他系統(tǒng)環(huán)境)和跑在上面的應(yīng)用磅摹。
查看容器狀態(tài)
docker ps //正在運(yùn)行的容器顯示
docker container ls
docker ps –a
docker container ls –a
如下將具體介紹如何來管理一個(gè)容器滋迈,包括創(chuàng)建、啟動(dòng)和停止等户誓。
Docker 啟動(dòng)容器
啟動(dòng)容器有三種方式饼灿,一種是基于鏡像新建一個(gè)容器并啟動(dòng),一種是將在終止?fàn)顟B(tài)(stopped)的容器重新啟動(dòng)帝美。
新建并啟動(dòng)
所需要的命令主要為 docker run
下面的命令則啟動(dòng)一個(gè) bash 終端碍彭,允許用戶進(jìn)行交互
docker run -it 鏡像 bash
其中,-t 選項(xiàng)讓Docker分配一個(gè)偽終端(pseudo-tty)并綁定到容器的標(biāo)準(zhǔn)輸入上悼潭, -i 則讓容器的標(biāo)準(zhǔn)輸入保持打開庇忌。
在交互模式下,用戶可以通過所創(chuàng)建的終端來輸入命令舰褪,例如
當(dāng)利用 docker run 來創(chuàng)建容器時(shí)皆疹,Docker 在后臺(tái)運(yùn)行的標(biāo)準(zhǔn)操作包括:
檢查本地是否存在指定的鏡像,不存在就從公有倉(cāng)庫(kù)下載
利用鏡像創(chuàng)建并啟動(dòng)一個(gè)容器
分配一個(gè)文件系統(tǒng)占拍,并在只讀的鏡像層外面掛載一層可讀寫層
從宿主主機(jī)配置的網(wǎng)橋接口中橋接一個(gè)虛擬接口到容器中去
從地址池配置一個(gè) ip 地址給容器
執(zhí)行用戶指定的應(yīng)用程序
執(zhí)行完畢后容器被終止
啟動(dòng)已終止容器
可以利用 docker start 命令墙基,直接將一個(gè)已經(jīng)終止的容器啟動(dòng)運(yùn)行
docker stop 9be696a0c283 //停止正運(yùn)行容器(或Ctrl+c)
docker restart 9be696a0c283//啟動(dòng)容器 (根據(jù) ID或NAMES)
如果根據(jù)容器名稱,可通過參數(shù) - - name 來自定義名稱
docker run --rm -p 8081:8080 --name myTomcat 鏡像名稱
Docker 守護(hù)態(tài)運(yùn)行
更多的時(shí)候刷喜,需要讓 Docker 在后臺(tái)運(yùn)行而不是直接把執(zhí)行命令的結(jié)果輸出在當(dāng)前宿主機(jī)下。此時(shí)立砸,可以通過添加 -d 參數(shù)來實(shí)現(xiàn)
如果不使用 -d 參數(shù)運(yùn)行容器:將會(huì)在當(dāng)前宿主機(jī)運(yùn)行掖疮。
如果使用了 -d 參數(shù)運(yùn)行容器。此時(shí)容器會(huì)在后臺(tái)運(yùn)行并不會(huì)把輸出的結(jié)果 (STDOUT) 打印到宿主機(jī)上面(輸出結(jié)果可以用 docker logs查看)颗祝。
docker run --rm --name myTomcat -d -p 8081:8080 鏡像名
查看控制臺(tái)結(jié)果:
docker logs myTomcat //(ID或Names)
Docker 終止容器
docker stop 9be696a0c283 //停止正運(yùn)行容器(或Ctrl+c)
docker container stop myTomcat//停止正運(yùn)行容器(ID或Names)
Docker 進(jìn)入容器
某些時(shí)候需要進(jìn)入容器進(jìn)行操作浊闪,包括使用 docker attach 命令或 docker exec 命令恼布,推薦大家使用 docker exec 命令
exec 命令
-i -t 參數(shù)
docker exec 后邊可以跟多個(gè)參數(shù),這里主要說明 -i -t 參數(shù)搁宾。
只用 -i 參數(shù)時(shí)折汞,由于沒有分配偽終端,界面沒有我們熟悉的 Linux 命令提示符盖腿,但命令執(zhí)行結(jié)果仍然可以返回爽待。
當(dāng) -i -t 參數(shù)一起使用時(shí),則可以看到我們熟悉的 Linux 命令提示符翩腐。
docker exec –it 容器ID(Names) bash
區(qū)別:如果從這個(gè) stdin 中 exit鸟款,不會(huì)導(dǎo)致容器的停止。
Docker 刪除容器
可以使用 docker container rm 或 docker rm 來刪除一個(gè)處于終止?fàn)顟B(tài)的容器茂卦。
清理所有處于終止?fàn)顟B(tài)的容器
用 docker container ls -a 命令可以查看所有已經(jīng)創(chuàng)建的包括終止?fàn)顟B(tài)的容器何什,如果數(shù)量太多要一個(gè)個(gè)刪除可能會(huì)很麻煩,用下面的命令可以清理掉所有處于終止?fàn)顟B(tài)的容器
docker container prune 或 docker prune
Docker 導(dǎo)出容器
http://www.runoob.com/
docker export :將文件系統(tǒng)作為一個(gè)tar歸檔文件導(dǎo)出到STDOUT
-o 參數(shù):將輸入內(nèi)容寫到文件等龙。
實(shí)例
將id為a404c6c174a2的容器按日期保存為tar文件
docker export -o tomcat-`date +%Y%m%d`.tar 9be696a0c283
注意: `` 號(hào)是Esc下的按鍵处渣。 date + 中要求有空格。
Docker 導(dǎo)入容器
docker import : 從歸檔文件中創(chuàng)建鏡像蛛砰。
語法
docker import [OPTIONS] file|URL|- [REPOSITORY[:TAG]]
-c :應(yīng)用docker 指令創(chuàng)建鏡像罐栈;
-m :提交時(shí)的說明文字;
實(shí)例
從鏡像歸檔文件tomcat-20190116.tar 創(chuàng)建鏡像暴备,命名為tomcat_1:1.0
docker import tomcat-20190116.tar tomcat_1:1.0
可通過此處查看鏡像交互內(nèi)容:
docker run -it tomcat_1:1.0 bash
Docker 安裝MySQL
參考:http://www.runoob.com/docker/docker-install-mysql.html
1悠瞬、查看本地鏡像
docker images
2、搜索鏡像
docker search mysql
3涯捻、下載鏡像
docker pull mysql:5.6
創(chuàng)建并啟動(dòng)MySQL容器
docker run -d --name mysql3306 -p 3306:3306 -e MYSQL_ROOT_PASSWORD='guoweixin' mysql:5.6
docker run -d
--name mysql3306
-p 3306:3306
-e MYSQL_ROOT_PASSWORD='guoweixin'
mysql:5.6
5浅妆、訪問測(cè)試
進(jìn)入到容器內(nèi)部
docker exec -it mysql3306 bash
連接mysql數(shù)據(jù)庫(kù):
mysql -u root -p
輸入數(shù)據(jù)庫(kù)密碼
授權(quán)其他機(jī)器登陸
1、授權(quán)主機(jī)訪問:MySQL>GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' IDENTIFIED BY 'guoweixin' WITH GRANT OPTION;
2障癌、刷新權(quán)限:MySQL>FLUSH PRIVILEGES;
3凌外、退出:MySQL>EXIT;
注意:(如果阿里云服務(wù)器部署和訪問,防火墻默認(rèn)是關(guān)閉的涛浙,需要手動(dòng)開啟)
https://www.cnblogs.com/kccdzz/p/8110143.html
阿里云控制組中加入該權(quán)限:
https://blog.csdn.net/yenange/article/details/89499840
Docker 查看日志
Docker查看日志
docker logs 容器名稱/ID
docker logs -f -t --since="2018-12-1" --tail=10 qfjy_exam
--since : 此參數(shù)指定了輸出日志開始日期康辑,即只輸出指定日期之后的日志。
-f : 查看實(shí)時(shí)日志
-t : 查看日志產(chǎn)生的日期
-tail=10 : 查看最后的10條日志
qfjy_exam : 容器名稱
Docker 總結(jié)
Docker服務(wù)的操作:
systemctl start docker 啟動(dòng)鏡像
systemctl stop docker 停止鏡像
systemctl restart docker 重啟鏡像
Docker就是來裝軟件的轿亮,比如:Tomcat疮薇、Redis、MySQL等
安裝容器步驟:
1我注、查詢本地鏡像
docker images
2按咒、搜索倉(cāng)庫(kù)找中的鏡像
docker search 鏡像名稱
比如:
搜索Tomcat
docker search tomcat
3、下載鏡像
docker pull 名稱:版本號(hào)
4但骨、創(chuàng)建容器
docker create --name 容器名稱 -p 宿主端口號(hào):容器端口號(hào) -v 宿主路徑:容器路徑 鏡像名稱:版本號(hào)
5励七、啟動(dòng)容器
docker start 容器名稱
6智袭、訪問測(cè)試
Docker 安裝Redis
安裝單機(jī)版Redis
1、搜索redis
docker search redis
2掠抬、下載鏡像
docker pull redis:4.0.1
3吼野、創(chuàng)建并運(yùn)行容器
docker run --rm -d --name redis6379 -p 6379:6379 redis:4.0.1 --requirepass "guoweixin"
docker run --rm
-d
--name redis6379
-p 6379:6379 redis:4.0.1
--requirepass "guoweixin" //設(shè)置redis密碼
阿里云訪問設(shè)置Redis:
http://www.reibang.com/p/d9d70c3559c4
4、測(cè)試Redis
docker exec -it redis6379 bash //進(jìn)入redis命令
redis-cli //開啟客戶端功能
安裝集群版Redis-Cluster
https://note.youdao.com/ynoteshare1/index.html?id=d298d8971662d9ce930b7d939632872f&type=notebook#/
Docker 數(shù)據(jù)卷
問題:通過鏡像創(chuàng)建一個(gè)容器两波。容器一旦被銷毀瞳步,則容器內(nèi)的數(shù)據(jù)將一并被刪除。但有些情況下雨女,通過服務(wù)器上傳的圖片出會(huì)丟失谚攒。容器中的數(shù)據(jù)不是持久化狀態(tài)的。
那有沒有一種獨(dú)立于容器氛堕、提供持久化并能服務(wù)于多個(gè)容器的東西呢馏臭?
數(shù)據(jù)卷 : 是一個(gè)可供一個(gè)或多個(gè)容器使用的特殊目錄
特性:
數(shù)據(jù)卷可以在容器之間共享和重用
對(duì)數(shù)據(jù)卷的修改會(huì)立馬生效
對(duì)數(shù)據(jù)卷的更新,不會(huì)影響鏡像
數(shù)據(jù)卷默認(rèn)會(huì)一直存在讼稚,即使容器被刪除
為什么需要數(shù)據(jù)卷括儒?
這得從 docker 容器的文件系統(tǒng)說起。出于效率等一系列原因锐想,docker 容器的文件系統(tǒng)在宿主機(jī)上存在的方式很復(fù)雜帮寻,這會(huì)帶來下面幾個(gè)問題:
不能在宿主機(jī)上很方便地訪問容器中的文件。
無法在多個(gè)容器之間共享數(shù)據(jù)赠摇。
當(dāng)容器刪除時(shí)固逗,容器中產(chǎn)生的數(shù)據(jù)將丟失。
為了解決這些問題藕帜,docker 引入了數(shù)據(jù)卷(volume) 機(jī)制烫罩。數(shù)據(jù)卷是存在于一個(gè)或多個(gè)容器中的特定文件或文件夾,這個(gè)文件或文件夾以獨(dú)立于 docker 文件系統(tǒng)的形式存在于宿主機(jī)中洽故。數(shù)據(jù)卷的最大特定是:其生存周期獨(dú)立于容器的生存周期贝攒。
使用數(shù)據(jù)卷的最佳場(chǎng)景
在多個(gè)容器之間共享數(shù)據(jù),多個(gè)容器可以同時(shí)以只讀或者讀寫的方式掛載同一個(gè)數(shù)據(jù)卷时甚,從而共享數(shù)據(jù)卷中的數(shù)據(jù)隘弊。
當(dāng)宿主機(jī)不能保證一定存在某個(gè)目錄或一些固定路徑的文件時(shí),使用數(shù)據(jù)卷可以規(guī)避這種限制帶來的問題荒适。
當(dāng)你想把容器中的數(shù)據(jù)存儲(chǔ)在宿主機(jī)之外的地方時(shí)梨熙,比如遠(yuǎn)程主機(jī)上或云存儲(chǔ)上。
當(dāng)你需要把容器數(shù)據(jù)在不同的宿主機(jī)之間備份刀诬、恢復(fù)或遷移時(shí)串结,數(shù)據(jù)卷是很好的選擇。
參考文獻(xiàn)(后續(xù)閱讀):
https://blog.csdn.net/jiangyu1013/article/details/80881097
https://www.jb51.net/article/135904.htm
創(chuàng)建一個(gè)數(shù)據(jù)卷
docker volume create my-vol
查看所有的 數(shù)據(jù)卷
docker volume ls
案例:現(xiàn)在將公共的資源images放入數(shù)據(jù)卷,進(jìn)行各容器啟動(dòng)訪問
Docker部署springboot項(xiàng)目
http://www.reibang.com/p/2909593e30ed
docker run -d --name blog-web -p 8443:8443 blog-web
docker run -d --name blog-web -p 8080:8443 blog-web