我们的开发人员和布署人员经常因环境问题,而使得安装过程困难重重,相比于虚拟机较少硬件资源的虚拟化,同时不需要加载虚拟机操作系统的耗时,因为docker共享宿主机的操作系统
Centos和Ubunta共用内核kernel即bootfs相同,但是加载内核的rootfs不同,即文件的结构目录不同
docker三要素
docker可以看作为一个小型的linux系统,部署时秒级启动
- 镜像:模板(应用程序代码),一个镜像可以实例多个容器
- 容器:镜像的实例
- 仓库:集中存放镜像的地方,分为公有仓库和私有仓库
配置文件位置:/etc/docker/daemon.json
dockerfile解析
定义:对image的描述
- FROM:base镜像(scratch:所有镜像的基础)
- WORKDIR:进入container后的落脚点
- ADD:将指定内容加到镜像里,并解压
- COPY原路径 目的路径:将指定内容加到镜像里
- LABEL:注释
- RUN:执行的命令
- CMD:container运行时执行的命令,可以执行多条只有最后一条生效
- ENTRYPOINT运行时执行的命令,可以执行多条
- EXPOSE:暴露端口
- ENV XXX XXX:环境变量
- ONBUILD:被子镜像继承后触发
总结:上述参数每执行到一行相当于一次commit,对原有镜像进行一次封装
docker常用命令
- 查看docker
docker version
docker info
docker inspect 【container-id】:以json格式描述docker
docker history 【container-id】
- 列出本地镜像
docker images
docker images -a : 千层饼的多层显示出来
docker images -q :显示镜像id
- 从docker hub搜索镜像
docker search -s 30 【tomcat】:只显示搜索超过30的镜像
- 删除镜像
docker rmi 【镜像】删除多个镜像中间以空格分隔
- 修改镜像
docker commit -a "alice" -m "commit" 【container-id】【包名/类名:tag】
-a:作者信息
-m:备注信息
包名/类名:tag:全部可以自定义
- build镜像
docker build .
-f 【dockerfile文件位置】
-t 【包名/类名:tag】
不写-v,默认会生成默认的连接目录
如果出现权限问题的解决方案:--previleged=true
- 创建容器并运行
docker run 镜像 (如果本地有就用本地的,如果没有就去dockerhub拉取)/bin/sh
-it: 交互式响应并弹出伪终端
-d:后台运行
-rm:容器使用完自动删除
:latest : 镜像的默认tag
--name:给容器起名
-p 8801:8080:对外暴漏的docker的端口是8801,docker里面tomcat的端口是8080,此时完成在docker里面启动tomcat
-P :用随机分配的端口启动tomcat,tomcat是镜像,启动镜像的实例
-v /宿主机绝对目录:/容器内的目录 :容器和主机之间进行数据共享,若目录不存在均会自动创建
-v /宿主机绝对目录:/容器内的目录:ro :容器内共享目录侧只读,但可以同步宿主机的修改
-volumes-from 【container-name/container-id】:继承其他container的volume,实现container之间数据共享,即使主container被删除,子container之间仍然能共享数据
/bin/sh:可以替换成其他,相当于CMD执行的语句
- 停止容器
docker stop 【container-id】:温柔停止
docker kill【container-id】:暴力停止,相当于直接拔电源
- 删除已停止的容器
docker rm【container-id】
docker rm -f $(docker ps -q): 删除全部容器
- 查看docker的container-id
docker ps -a
- 进入到该container的代码里,然后正常使用
docker exec -it 03df4594c149 /bin/sh(可以使用其他命令,比如ls)
- 查看container里运行的进程(如下图就是postgres数据库)
docker top 03df4594c149
- 查看docker的log
docker logs -f 【container-id】
-t :显示时间戳
docker可以在centos里下载centos镜像,此镜象没有Linux内核和操作系统等元素,大小会较少很多,这也是docker轻量级的原因
Repository是Docker存放镜像的场所。
volumn:这对于在主机和容器之间共享文件,
docker etcd:默认 2379 端口是给client 连接用的,而 2380 则在etcd 集群 各个节点之间交互用的,本机下发/撤回时是通过ETCD集群post发送给peer,peer的地址就是remote-address
Docker Host: 安装了docker的Linux系统
下面介绍通过python的docker包实现创建容器
- 创建docker客户端
import docker
# base_url:链接路径,可以通过socket或者tcp(ip:port)方式链接
# 举例:"unix:///var/run/docker.sock" or "tcp://127.0.0.1:8801".
client = docker.DockerClient(base_url="", version="auto")
- 创建container
# volumes: 字典配置,将外部数据卷挂载到容器内部,key是主机或者数据卷的名字(外部),value是带有key的字典
# detach :默认'True',他将立即返回一个Container对象,类似于'docker run -d'
# environment :内部环境变量
# publish_all_ports: 开放所有的端口到本机上 相当于docker run -P
# network: 网络模式 相当于docker run --net='host'
container = client.containers.create(
name="container",
image="",
detach=True,
publish_all_ports=True,
environment=[xx=zz],
network="",
volumes={'/home/user/': {'bind': '/mnt/vol2', 'mode': 'rw'},}
- 列出目前存活的容器
containers.list()
- 获取指定容器
# 参数可以是container的id or name
containers.get("xxx")
- 启动container
== 注意如果要创建大量container,会出现container端口冲突的情况,此时只能删除重建 ==
container.start()
- 停止container
stop前最好通过container.status先判断下container的状态
container.stop()
- 删除container
container.remove(force=True)