Docker 技术入门与实战 机械工业出版社
入门部分
初识 Docker
基本概念
- 虚拟化既可以通过硬件模拟,也可以通过操作系统来实现
- 完全虚拟化(vmware workstation/virtualbox/qemu)
- 硬件辅助虚拟化 - intel-vt & amd-v(vmware workstation/xen/kvm)
- 部分虚拟化
- 超虚拟化(paravirtualization)
- 操作系统级虚拟化
- centos 6.5/ubuntu 14.04/redhat 6.5 都已默认带有 docker 软件包
- Docker 主要目标是“ Build, Ship and Run Any App, Anywhere ”,「一次封装,到处运行」
- Docker 引擎的基础是 Linux 容器( LXC IBM 发起)技术
- 容器的创建和停止都十分快速,容器自身对资源的需求也十分有限,远远低于虚拟机
- 迁移只需要在服务器上启动需要的容器即可,节约大量的时间,降低部署产生问题的风险
与虚拟机相比的优势
- 启动和停止可以在秒级实现
- 对系统资源需求很少(一台主机可部署上千个 Docker 容器)
- 通过类似 git 的操作,方便用户获取/分发和更新应用镜像
- 通过 Dockerfile 配置文件支持灵活的自动化创建和部署机制
- 隔离性:安全选项和镜像签名机制
Docker 的核心概念与安装
核心概念
镜像(Image)
- 创建 Docker 容器的基础
容器(Container)
- 运行和隔离应用的轻量级沙箱
仓库(Repository)
- 集中存放镜像文件的场所
- 分为公开仓库和私有仓库
安装
ubuntu(略)
centos
# centos 6
sudo yum install -y http://mirrors.yun-idc.com/epel/6/i386/epel-release-6-8.noarch.rpm
sudo yum install -y docker-io
# centos 7
sudo yum install -y docker
windows(略)
mac os(略)
镜像
获取镜像
sudo docker pull [repositoryURL[:repositoryURLPort]/]DockerImageName[:ImageTags]
// e.g.
sudo docker pull ubuntu:16.04 // e.g.1
sudo docker pull registry.hub.docker.com/ubuntu:latest // e.g.2 效果同上 e.g.1
sudo docker pull dl.dockerpool.com:5000/ubuntu // e.g.3
// 在本地 ubuntu 容器内运行 bash 应用
sudo docker run -t -i ubuntu /bin/bash
查看镜像信息
sudo docker images
包含信息
- repository - 来自的仓库 like, dl.dockerpool.com:5000/ubuntu
- tag - 镜像标签信息 like, 14.04 或 latest
- image id(唯一) - 镜像 ID like 5506de…
- created - 创建时间
- virtual size - 镜像大小
# 更改 tag
sudo docker tag dl.dockerpool.com:5000/ubuntu:latest ubuntu:latest
# 查看 image 详情信息
sudo docker inspect 5506de...
# 查看 image 中具体一项的信息
sudo docker inspect -f {{".Architecture"}} 5506de...
搜索镜像
sudo docker search xxx
参数
- -s, –stars=0 指定仅显示星级以上的镜像
- –automated=false 仅显示自动创建的镜像
- –no-trunc=false 输出信息不截断显示
删除镜像
sudo docker rmi dl.dockerpool.com:5000/ubuntu
# 有时需要先删除依赖该镜像的所有容器,再删除镜像
sudo docker rm xxxxx
sudo docker rmi xxxxx
# 查看本机上存在的所有容器
sudo docker ps -a
创建镜像
基于已有镜像的容器创建
docker commit [options] containerID [repositoryURL[:tag]]
// e.g.
sudo docker commit -m "add a new file" -a "docker NewBee" 5506de... test
参数
- -a, –author=”” 作者信息
- -m, –message=”” 提交信息
- -p, –pause=true 提交时暂停容器运行
基于本地模板导入
sudo cat ubuntu-14.04-x86_64-minimal.tar.gz |docker import - ubuntu:14.04
基于 Dockerfile 创建
详见下一章
存出和载入镜像
存出镜像
sudo docker save -o ubuntu_14.04.tar ubuntu:14.04
载入镜像
sudo docker load --input ubuntu_14.04.tar
// 或
sudo docker load < ubuntu_14.04.tar
上传镜像
sudo docker tag test:latest user/test:latest # 添加新标签 user/test:latest
sudo docker push user/test:latest # 上传镜像
容器
创建容器
run <=> create + start
sudo docker create -it ubuntu:latest
sudo docker start 5506de...
# 守护态运行 daemonized
sudo docker run -d ubuntu /bin/sh -c "while true; do echo hello world; sleep 1; done"
参数
- -i 让容器的标准输入保持打开
- -t 让 Docker 分配一个伪终端并绑定到容器的标准输入上
终止容器
sudo docker stop 5506de...
# 重启
sudo docker restart 5506de...
进入容器
使用 -d 参数,容器启动后会进入后台,用户无法看到容器中的信息
attach 命令
exec 命令
sudo docker exec -it 5506de... /bin/bash
nsenter 工具
删除容器
sudo docker rm 5506de...
参数
- -f, –force=false 强行终止并删除一个运行中的容器
- -l, –link=false 删除容器的连接,但保留容器
- -v, –volumes=false 删除容器挂载的数据卷
导入和导出容器
导出容器
sudo docker export 5506de... > test_for_run.tar
导入容器
cat test_for_run.tar | sudo docker import - test/ubuntu:v1.0
import 与 load 命令的区别在于前者是导入容器快照(当前的状态),后者是导入镜像存储文件(整个运行过程的每个状态),所以一般 load 的镜像文件更大
仓库
docker hub
docker pool
搭建一套私用的仓库
sudo docker run -d -p 5000:5000 -v /opt/data/registry:/tmp/registry registry
数据管理
数据卷
- -v [source:]destination[:ro/rw]
- –volumes-from containerVolumes
- –name VolumesName 挂载的 Volume 名称
- -P 允许外部访问容器需要暴露的端口
# 在容器内创建数据卷
sudo docker run -d -P --name web -v /webapp training/webapp python app.py
# 挂载主机目录作为数据卷
sudo docker run -d -P --name web -v /src/webapp:/opt/webapp training/webapp python app.py
# ro / rw
sudo docker run -d -P --name web -v /src/webapp:/opt/webapp:ro training/webapp python app.py
# 挂载一个本地主机文件作为数据卷
sudo docker run --rm -it -v ~/.bash_history:/.bash_history ubuntu /bin/bash
数据卷容器
sudo docker run -it -v /dbdata --name dbdata ubuntu
sudo docker run -it --volumes-from dbdata --name db1 ubuntu
sudo docker run -it --volumes-from db1 --name db3 training/postgres
利用数据卷容器迁移容器
备份
sudo docker run --volumes-from dbdata -v ${pwd}:/backup --name worker ubuntu
tar cvf /backup/backup.tar /dbdata
恢复
sudo docker run -v /dbdata --name dbdata2 ubuntu /bin/bash
sudo docker run --volumes-from dbdata2 -v ${pwd}:/backup busybox tar xvf /backup/backup.tar
网络基础配置
端口映射实现访问容器
# 从外部访问容器应用(随机映射 49000~49900)
sudo docker run -d -P training/webapp python app.py
# 查看应用 log 信息
sudo docker logs -f containerName
# 映射所有接口地址(可绑定多个端口)
sudo docker run -d -p 5000:5000 training/webapp python app.py
sudo docker run -d -p 5000:5000 -p 3000:80 training/webapp python app.py
# 映射到指定地址的指定端口
sudo docker run -d -p 127.0.0.1:5000:5000 training/webapp python app.py
# 映射到指定地址的任意端口
sudo docker run -d -p 127.0.0.1::5000 training/webapp python app.py
# 映射到指定地址的指定 udp 端口
sudo docker run -d -p 127.0.0.1:5000:5000/udp training/webapp python app.py
# 查看端口映射
sudo docker port containerName 5000
容器互联实现容器间通信
自定义容器名称(容器名称是唯一的)
–name containerName
# 查看 container name
sudo docker ps -l
# 或
sudo docker inspect -f "{{.Name}}" aed84
–rm 容器在终止后会立刻删除,且 –rm 与 -d 参数不能同时使用
容器互联
–link name:alias(没有用 -p 或 -P,避免暴露数据库端口到外部网络中)
sudo docker run -d -P --name web --link db:db training/webapp python app.py
Docker 通过两种方式为容器公开连接信息:
- 环境变量
- 更新 /etc/hosts 文件
高级特性