什么是docker
Docker 是一個開源項目祭椰,誕生于 2013 年初蔓榄,最初是 dotCloud 公司內(nèi)部的一個業(yè)余項目详恼。它基于 Google 公司推出的 Go 語言實現(xiàn)。 項目后來加入了 Linux 基金會坤溃,遵從了 Apache 2.0 協(xié)議拍霜,項目代碼在 GitHub 上進行維護。Docker 自開源后受到廣泛的關(guān)注和討論薪介,以至于 dotCloud 公司后來都改名為 Docker Inc祠饺。Redhat 已經(jīng)在其 RHEL6.5 中集中支持 Docker;Google 也在其 PaaS 產(chǎn)品中廣泛應(yīng)用汁政。Docker 項目的目標是實現(xiàn)輕量級的操作系統(tǒng)虛擬化解決方案道偷。 Docker 的基礎(chǔ)是 Linux 容器等技術(shù)。在 LXC 的基礎(chǔ)上 Docker 進行了進一步的封裝记劈,讓用戶不需要去關(guān)心容器的管理试疙,使得操作更為簡便。用戶操作 Docker 的容器就像操作一個快速輕量級的虛擬機一樣簡單抠蚣。
特點
作為一種新興的虛擬化方式祝旷,Docker 跟傳統(tǒng)的虛擬化方式相比具有眾多的優(yōu)勢。
Docker 在如下幾個方面具有較大的優(yōu)勢:
- 更快速的交付和部署
Docker在整個開發(fā)周期都可以完美的輔助你實現(xiàn)快速交付嘶窄。Docker允許開發(fā)者在裝有應(yīng)用和服務(wù)本地容器做開發(fā)怀跛。可以直接集成到可持續(xù)開發(fā)流程中柄冲。
例如:開發(fā)者可以使用一個標準的鏡像來構(gòu)建一套開發(fā)容器吻谋,開發(fā)完成之后,運維人員可以直接使用這個容器來部署代碼现横。 Docker 可以快速創(chuàng)建容器漓拾,快速迭代應(yīng)用程序,并讓整個過程全程可見戒祠,使團隊中的其他成員更容易理解應(yīng)用程序是如何創(chuàng)建和工作的骇两。 Docker 容器很輕很快!容器的啟動時間是秒級的姜盈,大量地節(jié)約開發(fā)低千、測試、部署的時間馏颂。 - 高效的部署和擴容
Docker 容器幾乎可以在任意的平臺上運行示血,包括物理機、虛擬機救拉、公有云难审、私有云、個人電腦亿絮、服務(wù)器等告喊。 這種兼容性可以讓用戶把一個應(yīng)用程序從一個平臺直接遷移到另外一個拂铡。Docker的兼容性和輕量特性可以很輕松的實現(xiàn)負載的動態(tài)管理。你可以快速擴容或方便的下線的你的應(yīng)用和服務(wù)葱绒,這種速度趨近實時感帅。 - 更高的資源利用率
Docker 對系統(tǒng)資源的利用率很高,一臺主機上可以同時運行數(shù)千個 Docker 容器地淀。容器除了運行其中應(yīng)用外失球,基本不消耗額外的系統(tǒng)資源,使得應(yīng)用的性能很高帮毁,同時系統(tǒng)的開銷盡量小实苞。傳統(tǒng)虛擬機方式運行 10 個不同的應(yīng)用就要起 10 個虛擬機,而Docker 只需要啟動 10 個隔離的應(yīng)用即可烈疚。 - 更簡單的管理
使用 Docker黔牵,只需要小小的修改,就可以替代以往大量的更新工作爷肝。所有的修改都以增量的方式被分發(fā)和更新猾浦,從而實現(xiàn)自動化并且高效的管理。
核心概念
- 鏡像
Docker 鏡像就是一個只讀的模板灯抛。例如:一個鏡像可以包含一個完整的操作系統(tǒng)環(huán)境金赦,里面僅安裝了 Apache 或用戶需要的其它應(yīng)用程序。鏡像可以用來創(chuàng)建 Docker 容器对嚼,一個鏡像可以創(chuàng)建很多容器夹抗。Docker 提供了一個很簡單的機制來創(chuàng)建鏡像或者更新現(xiàn)有的鏡像,用戶甚至可以直接從其他人那里下載一個已經(jīng)做好的鏡像來直接使用纵竖。 - 倉庫
倉庫是集中存放鏡像文件的場所漠烧。有時候會把倉庫和倉庫注冊服務(wù)器混為一談,并不嚴格區(qū)分靡砌。實際上已脓,倉庫注冊服務(wù)器上往往存放著多個倉庫,每個倉庫中又包含了多個鏡像乏奥,每個鏡像有不同的標簽摆舟。倉庫分為公開倉庫和私有倉庫兩種形式。最大的公開倉庫是 Docker Hub邓了,存放了數(shù)量龐大的鏡像供用戶下載。國內(nèi)的公開倉庫包括 時速云 媳瞪、網(wǎng)易云 等骗炉,可以提供大陸用戶更穩(wěn)定快速的訪問。當然蛇受,用戶也可以在本地網(wǎng)絡(luò)內(nèi)創(chuàng)建一個私有倉庫句葵。當用戶創(chuàng)建了自己的鏡像之后就可以使用 push 命令將它上傳到公有或者私有倉庫,這樣下次在另外一臺機器上使用這個鏡像時候,只需要從倉庫上 pull 下來就可以了乍丈。Docker 倉庫的概念跟 Git 類似剂碴,注冊服務(wù)器可以理解為 GitHub 這樣的托管服務(wù)。 - 容器
Docker 利用容器來運行應(yīng)用轻专。容器是從鏡像創(chuàng)建的運行實例忆矛。它可以被啟動、開始请垛、停止催训、刪除。每個容器都是相互隔離的宗收、保證安全的平臺漫拭。可以把容器看做是一個簡易版的 Linux 環(huán)境(包括root用戶權(quán)限混稽、進程空間采驻、用戶空間和網(wǎng)絡(luò)空間等)和運行在其中的應(yīng)用程序。容器的定義和鏡像幾乎一模一樣匈勋,也是一堆層的統(tǒng)一視角挑宠,唯一區(qū)別在于容器的最上面那一層是可讀可寫的。
常用命令
- 從公網(wǎng)拉取一個鏡像
docker pull images_name
- 查看已有的docker鏡像
docker images
- 查看鏡像列表
docker search nginx
- 啟動一個容器
docker run hello-world
- 導(dǎo)出鏡像
docker save -o image_name.tar image_name
- 刪除鏡像
docker rmi image_name
- 啟動一個容器
docker run --name=con_name images
--name #設(shè)置容器名
- 基于創(chuàng)建好的容器自定義docker鏡像
docker commit -m "con_name" con_id image_name
- 創(chuàng)建一個容器的同時進入這個容器
docker run -it --name=con_name images
-it #在啟動之后進入這個容器
- 創(chuàng)建一個容器颓影,放入后臺運行各淀,把物理機80端口映射到容器的80端口
docker run -d -p 81:80 image_name
#-p 參數(shù)說明
-p hostPort:containerPort
-p ip:hostPort:containerPort
-p ip::containerPort
-p hostPort:containerPort:udp
- 看容器的端口映射情況
docker port con_id
- 查看正在運行的容器
docker ps
- 查看所有的容器
docker ps -a
- 動態(tài)查看容器日志
docker logs -f con_name
- 進入容器
docker attach con_name
- 退出容器
# 方法一
exit
# 方法二
ctrl+p && ctrl+q (一起按,注意順序诡挂,退出后容器依然保持啟動狀態(tài))
- 刪除容器
docker rm con_name
#強制刪除需要加-f碎浇,不加-f不能刪除正在運行中的容器,非常危險璃俗,最好不用
- 查看docker網(wǎng)絡(luò)
docker network ls
- 創(chuàng)建一個docker網(wǎng)絡(luò)my-docker
docker network create -d bridge \
--subnet=192.168.0.0/24 \
--gateway=192.168.0.100 \
--ip-range=192.168.0.0/24 \
my-docker
- 利用剛才創(chuàng)建的網(wǎng)絡(luò)啟動一個容器
docker run --network=my-docker --ip=192.168.0.5 -itd --name=con_name -h lb01 image_name
--network #指定容器網(wǎng)絡(luò)
--ip #設(shè)定容器ip地址
-h #給容器設(shè)置主機名
- 查看容器pid
#方法一:
docker top con_name
#方法二:
docker inspect --format "{{.State.Pid}}" con_name
- 運行dockerfile并給dockerfile創(chuàng)建的鏡像建立名字
docker build -t mysql:3.6.34 `pwd`
mariadb容器啟動前需先設(shè)置密碼方法
docker run -d -P -e MYSQL_ROOT_PASSWORD=password img_id
docker修改鏡像名
docker tag imageid name:tag
- 進入docker容器腳本
cat nsenter.sh
PID=`docker inspect --format "{{.State.Pid}}" $1`
nsenter -t $PID -u --mount -i -n -p
docker-compose簡介
Docker-Compose項目是Docker官方的開源項目奴璃,負責(zé)實現(xiàn)對Docker容器集群的快速編排。Docker-Compose將所管理的容器分為三層城豁,分別是工程苟穆,服務(wù)以及容器。Docker-Compose運行目錄下的所有文件組成一個工程唱星,若無特殊指定工程名即為當前目錄名雳旅。一個工程當中可包含多個服務(wù),每個服務(wù)中定義了容器運行的鏡像间聊,參數(shù)攒盈,依賴。一個服務(wù)當中可包括多個容器實例哎榴,Docker-Compose并沒有解決負載均衡的問題型豁,因此需要借助其它工具實現(xiàn)服務(wù)發(fā)現(xiàn)及負載均衡僵蛛。Docker-Compose的工程配置文件默認為docker-compose.yml,可通過環(huán)境變量COMPOSE_FILE或-f參數(shù)自定義配置文件迎变,其定義了多個有依賴關(guān)系的服務(wù)及每個服務(wù)運行的容器充尉。使用一個Dockerfile模板文件,可以讓用戶很方便的定義一個單獨的應(yīng)用容器衣形。在工作中驼侠,經(jīng)常會碰到需要多個容器相互配合來完成某項任務(wù)的情況。例如要實現(xiàn)一個Web項目泵喘,除了Web服務(wù)容器本身泪电,往往還需要再加上后端的數(shù)據(jù)庫服務(wù)容器,甚至還包括負載均衡容器等纪铺。Compose允許用戶通過一個單獨的docker-compose.yml模板文件來定義一組相關(guān)聯(lián)的應(yīng)用容器為一個項目相速。Docker-Compose項目由Python編寫,調(diào)用Docker服務(wù)提供的API來對容器進行管理鲜锚。因此突诬,只要所操作的平臺支持Docker API,就可以在其上利用Compose來進行編排管理芜繁。
Docker-Compose安裝
- 下載Docker-Compose
sudo curl -L https://github.com/docker/compose/releases/download/1.23.0-rc3/docker-compose-`uname -s`-`uname -m` -o /usr/local/bin/docker-compose
- 安裝Docker-Compose:
sudo chmod +x /usr/local/bin/docker-compose
- 查看版本 :
docker-compose version
- Docker-Compose卸載
- 如果是二進制包方式安裝的旺隙,刪除二進制文件即可:
sudo rm /usr/local/bin/docker-compose
- 如果通過Python pip工具安裝的,則執(zhí)行如下命令刪除:
sudo pip uninstall docker-compose
Docker-Compose模板文件
- Docker-Compose模板文件簡介
Compose允許用戶通過一個docker-compose.yml模板文件來定義一組相關(guān)聯(lián)的應(yīng)用容器為一個項目骏令。Compose模板文件是一個定義服務(wù)蔬捷、網(wǎng)絡(luò)和卷的YAML文件。Compose模板文件默認路徑是當前目錄下的docker-compose.yml榔袋,可以使用.yml或.yaml作為文件擴展名周拐。Docker-Compose標準模板文件應(yīng)該包含version、services凰兑、networks 三大部分妥粟,最關(guān)鍵的是services和networks兩個部分。
version: '2'
services:
web:
image: dockercloud/hello-world
ports:
- 8080
networks:
- front-tier
- back-tier
redis:
image: redis
links:
- web
networks:
- back-tier
lb:
image: dockercloud/haproxy
ports:
- 80:80
links:
- web
networks:
- front-tier
- back-tier
volumes:
- /var/run/docker.sock:/var/run/docker.sock
networks:
front-tier:
driver: bridge
back-tier:
driver: bridge
Compose目前有三個版本分別為Version 1吏够,Version 2勾给,Version 3,Compose區(qū)分Version 1和Version 2(Compose 1.6.0+锅知,Docker Engine 1.10.0+)播急。Version 2支持更多的指令。Version 1將來會被棄用喉镰。
- image
image是指定服務(wù)的鏡像名稱或鏡像ID旅择。如果鏡像在本地不存在,Compose將會嘗試拉取鏡像侣姆。
services:
web:
image: hello-world
- build
服務(wù)除了可以基于指定的鏡像生真,還可以基于一份Dockerfile,在使用up啟動時執(zhí)行構(gòu)建任務(wù)捺宗,構(gòu)建標簽是build柱蟀,可以指定Dockerfile所在文件夾的路徑。Compose將會利用Dockerfile自動構(gòu)建鏡像蚜厉,然后使用鏡像啟動服務(wù)容器长已。
build: /path/to/build/dir
也可以是相對路徑,只要上下文確定就可以讀取到Dockerfile昼牛。
build: ./dir
設(shè)定上下文根目錄术瓮,然后以該目錄為準指定Dockerfile。
build:
context: ../
dockerfile: path/of/Dockerfile
build都是一個目錄贰健,如果要指定Dockerfile文件需要在build標簽的子級標簽中使用dockerfile標簽指定胞四。如果同時指定image和build兩個標簽,那么Compose會構(gòu)建鏡像并且把鏡像命名為image值指定的名字伶椿。
- context
context選項可以是Dockerfile的文件路徑辜伟,也可以是到鏈接到git倉庫的url,當提供的值是相對路徑時脊另,被解析為相對于撰寫文件的路徑导狡,此目錄也是發(fā)送到Docker守護進程的context。
build:
context: ./dir
- dockerfile
使用dockerfile文件來構(gòu)建偎痛,必須指定構(gòu)建路徑
build:
context: .
dockerfile: Dockerfile-alternate
dockerfile指令不能跟image同時使用旱捧,否則Compose將不確定根據(jù)哪個指令來生成最終的服務(wù)鏡像。
- command
使用command可以覆蓋容器啟動后默認執(zhí)行的命令踩麦。
command: bundle exec thin -p 3000
- container_name
Compose的容器名稱格式是:<項目名稱><服務(wù)名稱><序號>
可以自定義項目名稱枚赡、服務(wù)名稱,但如果想完全控制容器的命名靖榕,可以使用標簽指定:
container_name: app
- depends_on
在使用Compose時标锄,最大的好處就是少打啟動命令,但一般項目容器啟動的順序是有要求的茁计,如果直接從上到下啟動容器料皇,必然會因為容器依賴問題而啟動失敗。例如在沒啟動數(shù)據(jù)庫容器的時候啟動應(yīng)用容器星压,應(yīng)用容器會因為找不到數(shù)據(jù)庫而退出践剂。depends_on標簽用于解決容器的依賴、啟動先后的問題娜膘。
version: '2'
services:
web:
build: .
depends_on:
- db
- redis
redis:
image: redis
db:
image: postgres
上述YAML文件定義的容器會先啟動redis和db兩個服務(wù)逊脯,最后才啟動web 服務(wù)。
- pid
pid: "host"
將PID模式設(shè)置為主機PID模式竣贪,跟主機系統(tǒng)共享進程命名空間军洼。容器使用pid標簽將能夠訪問和操縱其他容器和宿主機的名稱空間巩螃。 - ports
ports用于映射端口的標簽。
使用HOST:CONTAINER格式或者只是指定容器的端口匕争,宿主機會隨機映射端口避乏。
ports:
- "3000"
- "8000:8000"
- "49100:22"
- "127.0.0.1:8001:8001"
當使用HOST:CONTAINER格式來映射端口時,如果使用的容器端口小于60可能會得到錯誤得結(jié)果甘桑,因為YAML將會解析xx:yy這種數(shù)字格式為60進制拍皮。所以建議采用字符串格式。
- extra_hosts
添加主機名的標簽跑杭,會在/etc/hosts文件中添加一些記錄铆帽。
extra_hosts:
- "somehost:162.242.195.82"
- "otherhost:50.31.209.229"
啟動后查看容器內(nèi)部hosts:
162.242.195.82 somehost
50.31.209.229 otherhost
- volumes
掛載一個目錄或者一個已存在的數(shù)據(jù)卷容器,可以直接使用 [HOST:CONTAINER]格式德谅,或者使用[HOST:CONTAINER:ro]格式爹橱,后者對于容器來說,數(shù)據(jù)卷是只讀的女阀,可以有效保護宿主機的文件系統(tǒng)宅荤。
Compose的數(shù)據(jù)卷指定路徑可以是相對路徑,使用 . 或者 .. 來指定相對目錄浸策。數(shù)據(jù)卷的格式可以是下面多種形式:
volumes:
// 只是指定一個路徑冯键,Docker 會自動在創(chuàng)建一個數(shù)據(jù)卷(這個路徑是容器內(nèi)部的)。
- /var/lib/mysql
// 使用絕對路徑掛載數(shù)據(jù)卷
- /opt/data:/var/lib/mysql
// 以 Compose 配置文件為中心的相對路徑作為數(shù)據(jù)卷掛載到容器庸汗。
- ./cache:/tmp/cache
// 使用用戶的相對路徑(~/ 表示的目錄是 /home/<用戶目錄>/ 或者 /root/)惫确。
- ~/configs:/etc/configs/:ro
// 已經(jīng)存在的命名的數(shù)據(jù)卷。
- datavolume:/var/lib/mysql
如果不使用宿主機的路徑蚯舱,可以指定一個volume_driver改化。
volume_driver: mydriver
- volumes_from
從另一個服務(wù)或容器掛載其數(shù)據(jù)卷:
volumes_from:
- service_name
- container_name
- dns
自定義DNS服務(wù)器⊥骰瑁可以是一個值陈肛,也可以是一個列表。
dns:8.8.8.8
dns:
- 8.8.8.8
- 9.9.9.9
- dns_search
配置DNS搜索域兄裂【浜担可以是一個值,也可以是一個列表晰奖。
dns_search:example.com
dns_search:
- domain1.example.com
- domain2.example.com
- entrypoint
在Dockerfile中有一個指令叫做ENTRYPOINT指令谈撒,用于指定接入點。
在docker-compose.yml中可以定義接入點匾南,覆蓋Dockerfile中的定義:
entrypoint: /code/entrypoint.sh
- env_file
在docker-compose.yml中可以定義一個專門存放變量的文件啃匿。
如果通過docker-compose -f FILE指定配置文件,則env_file中路徑會使用配置文件路徑。如果有變量名稱與environment指令沖突溯乒,則以后者為準夹厌。格式如下:
env_file: .env
或者根據(jù)docker-compose.yml設(shè)置多個:
env_file:
- ./common.env
- ./apps/web.env
- /opt/secrets.env
如果在配置文件中有build操作,變量并不會進入構(gòu)建過程中橙数。
- cap_add
增加指定容器的內(nèi)核能力(capacity)尊流。
讓容器具有所有能力可以指定:
cap_add:
- ALL
- cap_drop
去掉指定容器的內(nèi)核能力(capacity)帅戒。去掉NET_ADMIN能力可以指定:
cap_drop:
- NET_ADMIN
- cgroup_parent
創(chuàng)建了一個cgroup組名稱為cgroups_1:
cgroup_parent: cgroups_1
- devices
指定設(shè)備映射關(guān)系灯帮,例如:
devices:
- "/dev/ttyUSB1:/dev/ttyUSB0"
22、expose
暴露端口逻住,但不映射到宿主機钟哥,只允許能被連接的服務(wù)訪問。僅可以指定內(nèi)部端口為參數(shù)瞎访,如下所示:
expose:
- "3000"
- "8000"
- extends
基于其它模板文件進行擴展腻贰。例如,對于webapp服務(wù)定義了一個基礎(chǔ)模板文件為common.yml:
# common.yml
webapp:
build: ./webapp
environment:
- DEBUG=false
- SEND_EMAILS=false
再編寫一個新的development.yml文件扒秸,使用common.yml中的webapp服務(wù)進行擴展:
# development.yml
web:
extends:
file: common.yml
service: webapp
ports:
- "8000:8000"
links:
- db
environment:
- DEBUG=true
db:
image: mysql
后者會自動繼承common.yml中的webapp服務(wù)及環(huán)境變量定義播演。
extends限制如下:
A、要避免出現(xiàn)循環(huán)依賴
B伴奥、extends不會繼承l(wèi)inks和volumes_from中定義的容器和數(shù)據(jù)卷資源
推薦在基礎(chǔ)模板中只定義一些可以共享的鏡像和環(huán)境變量写烤,在擴展模板中具體指定應(yīng)用變量、鏈接拾徙、數(shù)據(jù)卷等信息
- external_links
鏈接到docker-compose.yml外部的容器洲炊,可以是非Compose管理的外部容器。
external_links:
- redis_1
- project_db_1:mysql
- project_db_1:postgresql
- labels
為容器添加Docker元數(shù)據(jù)(metadata)信息尼啡。例如暂衡,可以為容器添加輔助說明信息:
labels:
com.startupteam.description: "webapp for a strtup team"
- links
鏈接到其它服務(wù)中的容器。使用服務(wù)名稱(同時作為別名)崖瞭,或者“服務(wù)名稱:服務(wù)別名”(如 SERVICE:ALIAS)狂巢,例如:
links:
- db
- db:database
- redis
使用別名將會自動在服務(wù)容器中的/etc/hosts里創(chuàng)建。例如:
172.17.2.186 db
172.17.2.186 database
172.17.2.187 redis
- log_driver
指定日志驅(qū)動類型书聚。目前支持三種日志驅(qū)動類型:
log_driver: "json-file"
log_driver: "syslog"
log_driver: "none"
- log_opt
日志驅(qū)動的相關(guān)參數(shù)唧领。例如:
log_driver: "syslog"log_opt:
syslog-address: "tcp://192.168.0.42:123"
- net
設(shè)置網(wǎng)絡(luò)模式。
net: "bridge"
net: "none"
net: "host"
- security_opt
指定容器模板標簽(label)機制的默認屬性(用戶寺惫、角色疹吃、類型、級別等)西雀。例如萨驶,配置標簽的用戶名和角色名:
security_opt:
- label:user:USER
- label:role:ROLE
- 環(huán)境變量
環(huán)境變量可以用來配置Docker-Compose的行為。
COMPOSE_PROJECT_NAME
設(shè)置通過Compose啟動的每一個容器前添加的項目名稱艇肴,默認是當前工作目錄的名字腔呜。
COMPOSE_FILE
設(shè)置docker-compose.yml模板文件的路徑叁温。默認路徑是當前工作目錄。
DOCKER_HOST
設(shè)置Docker daemon的地址核畴。默認使用unix:///var/run/docker.sock膝但。 DOCKER_TLS_VERIFY
如果設(shè)置不為空,則與Docker daemon交互通過TLS進行谤草。
DOCKER_CERT_PATH
配置TLS通信所需要的驗證(ca.pem跟束、cert.pem 和 key.pem)文件的路徑,默認是 ~/.docker 丑孩。