docker image 相關(guān)操作
- 顯示所有 image
docker images = docker image ls
- 拉去 registry 中的已有 image
docker pull image-name
- 刪除 image
# docker rmi = docker image rm
docker rmi image-ID
- 根據(jù)一個 Dockerfile 構(gòu)建一個 image (推薦使用該方式來創(chuàng)建逢慌,方便分享給他人使用)
docker build = docker image build
- 制定文件 Dockerfile 創(chuàng)建 image
docker build -t create-image-name Dockerfile-path
- 查看 image 的創(chuàng)建歷史
docker history image-ID
docker container 相關(guān)操作
- 顯示所有正在運(yùn)行的容器
docker ps = docker container ls
- 顯示所有容器(包括推出的容器)
docker ps -a
- 停止運(yùn)行的容器
# docker stop = docker container stop
docker stop container-ID/container-name
- 單個單個刪除容器 - 容器必須是退出狀態(tài)
# docker rm = docker container rm
docker rm container-ID/container-name
- 顯示所有容器的 ID,'-q' 只顯示容器 ID 號
docker ps -aq
- 刪除多個容器
docker rm $(docker ps -aq)
- 顯示已經(jīng)退出的容器 ID
docker ps -f "status=exited" -q
- 刪除已經(jīng)退出的容器
docker rm $(docker ps -f "status=exited" -q)
- 根據(jù)一個 container 的修改創(chuàng)建新的 image (不推薦使用該方式佣蓉,建議使用 Dockerfile 的形式)
# docker commit = docker container commit
docker commit old-container-namae new-image-name
- 查看容器詳細(xì)信息
# docker inspect = docker contaienr inspect
docker inspect container-ID
- 查看容器運(yùn)行時產(chǎn)生的日志
# docker logs = docker container logs
docker logs container-ID
docker run 相關(guān)操作
- 交互式運(yùn)行一個 image
docker run -it image-name
- 后臺執(zhí)行
docker run -d image-name
- 定義名字運(yùn)行容器
# 定義名字的容器是唯一的
docker run -d --name=demo image-name
docker stop demo
docekr rm demo
docker start demo
- 類似網(wǎng)絡(luò) NDS 愁溜,通過名稱連接容器之間的網(wǎng)絡(luò)
docker run -d --name test1 image-name
dokcer run -d --name test2 --link test1 image-name
# 在 test2 容器中可以直接使用容器 test1 來訪問網(wǎng)絡(luò)
docker exec -it test2 ping test1
- 啟動時指明使用的網(wǎng)絡(luò)
# 新的網(wǎng)絡(luò)可以通過 docker network create 來創(chuàng)建
docker run --network network-name image-name
- 端口映射
# 將容器的 80 端口映射到 docker 主機(jī)的 80 端口
docker run -p 80:80 image-name
- 設(shè)置環(huán)境變量
# 設(shè)置 demo 的環(huán)境 REDIS_HOST 的值為 redis 容器的 IP 地址
docker run --name demo --link redis -e REDIS_HOST=redis image-name
- 指定 volume
# 在 Dockerfile 中定義 VOLUME ["/var/lib/mysql"]
# 指定從 mysql 鏡像中創(chuàng)建的容器的 volume 在 /var/lib/mysql 中
docker run -v mysql:/var/lib/mysql --name mysql1 mysql
docker exec 相關(guān)操作
可以進(jìn)入在運(yùn)行中或停止運(yùn)行的容器中操作相關(guān)的命令
- 交互式進(jìn)入后執(zhí)行 /bin/bash 進(jìn)行命令操作
docker exec -it container-ID /bin/bash
- 交互式進(jìn)入后執(zhí)行 python 進(jìn)入 python 解釋器
docker exec -it container-ID python
- 交互式進(jìn)入后執(zhí)行 ip a 查看運(yùn)行中的容器 IP 地址
docker exec -it container-ID ip a
Dockerfile 語法
FROM
盡量使用官方的 image 作為 base image (比較安全)
# 制作 base image
FROM scratch
# 使用 base image
FROM centos
FROM UBUNTU:14.04
LABEL
Metadata 不可少
LABEL maintainer="caojiacan0618@gmail.com"
LABEL version="1.0"
LABEL description="This is description"
RUN
為了美觀又官,復(fù)雜的RUN請用反斜線換行
避免無用分層,合并多條命令成一行
# 反斜線換行
RUN yum update && yum install -y vim \
python-dev
# 注意清理 cache
RUN apt-get update && apt-get install -y perl \
pwgen --no-install-recommends && rm -rf \
/var/lib/apt/lists/*
RUN /bin/bash -c 'source $HOME/.bashrc; echo $HOME'
WORKDIR
作用類似 cd 命令
用 WORKDIR,不要使用 RUN cd
盡量使用絕對目錄
WORKDIR /root
# 如果沒有會自動創(chuàng)建 test 目錄
# 以下三行將會輸出 /test/demo
WORKDIR /test
WORKDIR demo
RUN pwd
ADD and COPY
大部分情況霎箍,COPY 優(yōu)于 ADD
ADD 除了 COPY 還有額外的功能(解壓)
添加遠(yuǎn)程文件/目錄請使用 curl 或者 wget
# 將當(dāng)前目錄的 hello 文件添加到 image 的根目錄下
ADD hello /
# 添加到根目錄,ADD 會執(zhí)行解壓縮澡为, COPY 不會執(zhí)行解壓縮
ADD test.tar.get /
# 講當(dāng)前目錄的 hello 文件漂坏,添加到 /root/test/ 目錄下
# 生成的容器中會存在一個 /root/test/hello 文件
WORKDIR /root
ADD hello test/
# 以下效果同上
WORKDIR /root
COPY hello test/
ENV
盡量使用 ENV 增加可維護(hù)性
# 設(shè)置常量 MYSQL_VERSION 為 5.6
ENV MYSQL_VERSION 5.6
# 引用常量
RUN apt-get install -y mysql-server="${MYSQL_VERSION}" \
&& rm -rf /var/lib/apt/lists/*
CMD and ENTRYPOINT
RUN:執(zhí)行命令并創(chuàng)建新的 Image Layer
CMD:設(shè)置容器啟動后默認(rèn)執(zhí)行的命令和參數(shù)
ENTRYPOINT:設(shè)置容器啟動時運(yùn)行的命令
# 以下通過 docker run [image] 輸出 hello $name 并不是想要結(jié)果
FROM centos
ENV name Docker
ENTRYPOINT echo "hello $name"
# 以下通過 docker run [image] 輸出 hello Docker 正是想要的結(jié)果
FROM centos
ENV name Docker
ENTRYPOINT ["/bin/bash", "-c", "echo hello $name"]
# cmd 補(bǔ)充說明
# 容器啟動時默認(rèn)執(zhí)行的命令
# 如果 docker run 制定了其他命令,CMD 命令被忽略
# 如果定義多個 CMD媒至,只有最后一個會執(zhí)行
# 以下通過 docker run [image] 輸出 hello Docker 正是想要的結(jié)果
FROM centos
ENV name Docker
CMD echo "hello $name"
# entrypoint 補(bǔ)充說明
# 讓容器以應(yīng)用程序或者服務(wù)的形式運(yùn)行
# 不會被忽略樊拓,一定執(zhí)行
# 最佳實(shí)踐:寫一個 shell 腳本作為 entrypoint
COPY docker-entrypoint.sh /usr/local/bin/
ENTRYPOINT ["docker-entrypoint.sh"]
EXPOSE 27017
CMD ["mongod"]
# CMD 和 ENTRYPOINT 結(jié)合使用
ENTRYPOINT ["/usr/bin/ls"]
CMD []
# 創(chuàng)建一個以上兩個語句組成的 image 后執(zhí)行
docker run iamge --> 輸出當(dāng)前目錄文件
docker run iamge -a --> 輸出當(dāng)前目錄所有文件
EXPOSE
# 使容器對外暴露 5000 端口
EXPOSE 5000
創(chuàng)建私有 Docker Hub
基本使用方法
- 從 Docker Hub 拉取官方 registry image
docker pull registry
- 啟動一個 registry container
docker run -d -p 5000:5000 --restart always --name registry registry:2
- 從 Docker Hub 拉取一個 ubuntu image
docker pull ubuntu
- 修改 ubuntu repository 名稱為私有 Docker Hub 啟動的主機(jī) IP + PORT + / + name
docker tag ubuntu localhost:5000/ubuntu
- 推送 image 到私有 Docker Hub 上
docker push localhost:5000/ubuntu
驗(yàn)證方法
# 刪除 localhost:5000/ubuntu 鏡像
docker rmi localhost:5000/ubuntu
# 重新從私有 Docker Hub 上拉取
docker pull localhost:5000/ubuntu
常用 HTTP API V2 接口
- GET /v2/_catalogu 顯示已有 image
容器物理資源限制
內(nèi)存 - Memory
只設(shè)置 memory 那么 memory-swap 默認(rèn)等于 memory,即占用兩倍設(shè)置的 memory
# 設(shè)置 memory 200M 和 memory-swap 200M 一共最多可使用 400M 內(nèi)存
# docker run --memory=200M = docker run -m 200M
docker run --memory=200M image-name
CPU
--cpu-shares 并不是設(shè)置 CPU 個數(shù)塘慕,而是設(shè)置相對權(quán)重
CPU 個數(shù)多的容器會優(yōu)先去使用資源的 CPU
在主機(jī) CPU 跑滿時筋夏,會根據(jù)設(shè)置的 CPU 個數(shù)呈現(xiàn)一個百分比關(guān)系
# docker run --cpu-shares=5 = docker run -c 5
docker run --cpu-shares=5 image-name
docker-machine 操作
- 列出所有 docker 虛擬機(jī)
docker-machine ls
- 創(chuàng)建一個 docker 虛擬機(jī)
docker-machine create docker-machine-name
- 啟動一個 docker 虛擬機(jī)
docker-machine start docker-machine-name
- 登錄一個 docker 虛擬機(jī)
docker-machine ssh docker-machine-name
-` 刪除一個 docker 虛擬機(jī)
docker-machine rm docker-machine-name
docker network
- 顯示本機(jī)所有的 docker 網(wǎng)絡(luò)
docke network ls
- 顯示使用對應(yīng) docker 網(wǎng)絡(luò)的容器
docker network inspect docker-network-id/docker-nwtwork-name
bridge 網(wǎng)絡(luò)
連接到自己創(chuàng)建的 bridge 網(wǎng)絡(luò)中的容器,默認(rèn)已經(jīng)相互 link图呢,可以直接使用容器名稱來訪問
- 創(chuàng)建一個 docker birdge 網(wǎng)咯
# docker network create -d 驅(qū)動名稱 新的網(wǎng)絡(luò)名稱
docker network create -d bridage my-bridage
- 將容器連接到指定的網(wǎng)絡(luò)
docker network connect network-name container-name
none 網(wǎng)絡(luò)
安全性高
# 誰都不能訪問的容器
docker run --network none image-name
host 網(wǎng)絡(luò)
容器出現(xiàn)端口沖突
# 和主機(jī)共享一套網(wǎng)絡(luò)
docker run --network host image-name
overlay 網(wǎng)絡(luò) - 實(shí)現(xiàn)多機(jī)通信
該網(wǎng)絡(luò)基于 VXLAN 方式實(shí)現(xiàn)類似隧道的功能
使用 overlay 網(wǎng)絡(luò)加分布式存儲 etcd 實(shí)現(xiàn)
持久化存儲和數(shù)據(jù)共享
持久化數(shù)據(jù)的方案
基于本地文件系統(tǒng)的 volume
受管理的 data volume条篷,由 docker 后臺自動創(chuàng)建
綁定掛載的 volume,具體掛載位置可以由用戶指定
可以在執(zhí)行 Docker create 或 Docker run 時蛤织,通過 -v 參數(shù)將主機(jī)的目錄作為容器的數(shù)據(jù)卷赴叹。這部分功能便是基于本地文系統(tǒng)的 volume 管理
- 查看所有 docker 管理的 volume
docker volume ls
- 刪除一個 volume
docker volume rm volume-name
- 查看 volume 詳細(xì)信息
docker volume inspect volume-name
data volume 方式
需要在 Dockerfile 中定義好存儲的目錄
# 在 Dockerfile 中定義 VOLUME ["/var/lib/mysql"]
# 指定從 mysql 鏡像中創(chuàng)建的容器的 volume 在 /var/lib/mysql 中
docker run -v mysql:/var/lib/mysql --name mysql1 mysql
Bind Mouting 方式
不需要在 Dockerfile 中定義
目錄映射的關(guān)系
Centos 7 下 使用 chcon -Rt httpd_sys_content_t . 關(guān)閉文本安全
或者使用 docker run --privileged=true 加特權(quán)
# 定義主機(jī)目錄和容器目錄
# -v 主機(jī)目錄:容器目錄
docker run -v /home/aaa:/root/aaa image-name
基于 plugin 的 volume
支持第三方的存儲方案,比如 NAS指蚜,aws
docker-compose 相關(guān)操作 - 默認(rèn)識別 docker-compose.yml 文件名
- Docker Compose 是一個工具
- 這個工具可以通過一個 yml 文件定義多容器的 docker 應(yīng)用
- 通過一條命令就可以根據(jù) yml 文件的定義去創(chuàng)建或者管理這個多容器
docker-compse.yml 文件語法
Services
一個 services 代表一個 container乞巧,這個 container 可以從 dockerhub 的 image 來創(chuàng)建,或者從本地的 Dockerfile build 出來的 image 來創(chuàng)建
Service 的啟動類似 container run摊鸡,我們可以給其指定 network 和 volume绽媒,所以可以給 service 指定 network 和 volume 的應(yīng)用
# 以下作用和 docker run -d --network back-tier -v db-data:/var/lib/postgresql/data/ postgres:9.4 命令相同
services:
db:
image: postgres:9.4
volumes:
- "db-data:/var/lib/postgresql/data"
networks:
- back-tier
# 以下作用是從 ./worker 目錄中的 Dockerfile 文件創(chuàng)建的 image 連接 db 和 reids 并連接在 back-tier 網(wǎng)絡(luò)中
services:
worker:
build: ./worker
links:
- db
- redis
networks:
- back-tier
Networks
# 以下作用和 docker network create -d bridge front-tier && docker network create -d bridge back-tier 命令相同
networks:
front-tier:
driver: bridge
back-tier:
driver: bridge
Volumes
# 以下作用和 docker volume create db-data 命令相同
volumes:
db-data:
完整的例子
version: '3'
services:
wordpress:
image: wordpress
ports:
- 8080:80
environment:
WORDPRESS_DB_HOST: mysql
WORDPRESS_DB_PASSWORD: root
# 依賴配置,指明先啟動依賴的容器
depends_on:
- mysql
networks:
- my-bridge
mysql:
image: mysql
environment:
MYSQL_ROOT_PASSWORD: root
MYSQL_DATABASE: wordpress
volumes:
- mysql-data:/var/lib/mysql
networks:
- my-bridge
volumes:
mysql-data:
networks:
my-bridge:
driver: bridge
docker-compose 命令行工具
用于本地開發(fā)免猾,不適用于生產(chǎn)環(huán)境
- 前臺啟動 container
docker-compose up
- 后臺啟動 container
docker-compose up -d
-刪除停止的 container
docker-compose down
- 查看運(yùn)行的 docker compose
docker-compose ps
- 指定啟動容器的個數(shù)
docker-compose up --scale container-name=num
- 預(yù)構(gòu)建 Dockerfile
docker-compose build
Swarm mode - 容器編排
- 管理更多容器
- 方便橫向擴(kuò)展
- 容器 down 了自動恢復(fù)
- 更新容器而不影響業(yè)務(wù)
- 監(jiān)控追蹤容器
- 調(diào)度容器的創(chuàng)建
- 保護(hù)隱私數(shù)據(jù)
初始化
先初始化 manager 節(jié)點(diǎn)
worker 節(jié)點(diǎn)使用生成的 token 進(jìn)行添加
- 進(jìn)入 manager 節(jié)點(diǎn)創(chuàng)建 swarm manager
docker swarm init --advertise-addr=swarm-manager-ip-addr
- 進(jìn)入 worker 節(jié)點(diǎn)加入 swarm manager
docker swarm join --token swarm-manager-join-token swarm-mananger-ip:swarm-manager-port
- 在 manager 節(jié)點(diǎn)管理 join token
docker swarm join-token manager
node 命令
- 顯示當(dāng)前 swarm 節(jié)點(diǎn)
docker node ls
service 命令
在 swarm 模式下一般不用 run 而使用 service
- 創(chuàng)建一個 service是辕,及運(yùn)行一個 container 并運(yùn)行
docker service create --name demo iamge
- 查看 service
docker service ls
- 刪除 service
docker service rm service-name
- 查看具體 service 內(nèi)容
docker service ps service-name
- 擴(kuò)展 service
docker service scale service-name=num
mode - 模式
- replicated 可以可以橫向擴(kuò)展
- global 不能做橫向擴(kuò)展
Routing Mesh 的兩種體現(xiàn)
- Internal - Container 和 Container 之間的訪問通過 overlay 網(wǎng)絡(luò) (通過 VIP 虛擬 IP)
- Ingress - 如果服務(wù)有綁定端口,則此服務(wù)可以通過任意 swarm 節(jié)點(diǎn)的相應(yīng)接口訪問
docker-compose.yml 中配置 deploy
官方文檔
網(wǎng)絡(luò)默認(rèn)使用 overlay
deploy:
# 定義模式為 replicated 可以橫行擴(kuò)展
mode: replicated
# 定義橫向擴(kuò)展 3 個容器
replicas: 3
# 配置運(yùn)行位置
placement:
# 指定容器運(yùn)行的節(jié)點(diǎn)
constraints:
- node.role == manager
# 配置重啟方案
restart_policy:
# 條件
condition: on-failure
# 延遲
delay: 5s
# 最大嘗試次數(shù)
max_attempts: 3
# 更新配置
update_config:
# 同時更新個數(shù)
parallelism: 2
# 延遲
delay: 10s
# 順序
order: stop-first
docker stack 部署 docker-compose.yml
stack 一次性啟動多個 service
- 啟動stack
# -c == -compose-file
docker stack deploy stack-name --compose-file=docker-compose.yml
- 查看所有 stack
docker stack ls
- 查看具體的 stack 運(yùn)行詳情
docker stack ps stack-name
- 查看概括的 service 運(yùn)行情況
docker stack service stack-name
update service
單個 service 更新步驟
docker service create -d --name server -p 8080:5000 image-name:1.0
# 使用 scale 擴(kuò)展
docker service scale server=2
# 更新 service 版本
dockeer service update --image image-name:2.0 server
# 更新 service 端口
dockeer service update --publish-rm 8080:5000 --publish-add 8888:5000 server
可視化工具
services:
visualizer:
image: dockersamples/visualizer:stable
ports:
- "8080:8080"
stop_grace_period: 1m30s
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
deploy:
placement:
constraints: [node.role == manager]
docker Secret Management
- 存在 Swarm Manager 節(jié)點(diǎn) Raft database 里
- Secret可以 assign 給一個 service猎提,這個 service 就能看到這個 secret
- 在 container 內(nèi)部 Secret 看起來像文件获三,但是實(shí)際是在內(nèi)存中
secret 管理
- 創(chuàng)建 secret - 文件方式
docker secret create secret-name secret-file
- 創(chuàng)建 secret - 命令行 echo 方式
echo "passwod" | docker secret create secret-name -
- 查看 secret - 源文件刪除了也可以查看到
docker secret ls
使用生成的 secret
- 創(chuàng)建 service 時指明 sercet
# 在容器中 /run/secrets/ 中存放傳入的 secret
docker service create --secret secret-name iamge-name
- 在 docker-compose.yml 文件中使用
# 前提是已經(jīng)創(chuàng)建了 secret
services:
app:
image: xxx
secrets:
- secret-name
environment:
SECRET_DEMO:/run/secrets/secret-name
- 在 docker-compose.yml 文件中創(chuàng)建和使用
# 不太推薦使用,相對上面一種安全性較低
services:
app:
image: xxx
secrets:
- secret-name
environment:
SECRET_DEMO:/run/secrets/secret-name
secrets:
secret-name:
file: secret-file-path