docker主机,也就是docker server端,通过http,https接受客户端的命令。docker daemon接受到命令后会在本地启动创建容器,一个docker主机上运行多个容器。容器启动基于镜像启动。如果没有镜像就会链接到docker registries。如下图:
获取镜像后存储在本地,这个存储是特殊的,在1.18后的版本使用的是overlay2的存储驱动。镜像本身是只读的,镜像在镜像registries上的名称和镜像应用程序名称是一样的。仓库内可以有多个镜像,或者多个不同镜像的不同版本。使用标签来识别这些镜像。
镜像的构建
镜像内包含有启动容器需要的文件系统和其他内容,作用在于创建并启动docker容器
docker采用了分层机制,最下层是bootfs,其中可以构建用户空间并且运行进程容器的是rootfs,如下图:
- bootfs
底层驱动有lxc,aufs/btrfs,这些用来引导启动一个用户空间,这里的kernel内核实现的功能仅仅用来启动和引导用户空间,容器启动完成后会被卸载以节约内存资源
- rootfs
位于bootfs之上,表现为docker容器的根文件系统
[root@Linuxea-Node_10_10_240_145 ~]$ docker exec -it nginx_createrepo bash
[root@Linuxea-Node_10_10_240_145 /]# ls
bin dev home lib64 mnt proc run srv sys usr
data etc lib media opt root sbin startup.sh tmp var
传统系统中,系统启动时候,根文件被挂载后会进行自检,为了避免自检时候出现错误而导致数据被误伤,在自检之前一般挂载的是只读,自检完成没有问题后才会重新挂载为读写模式。
而在docker中整个rootfs都是由内核挂载为"只读",而后通过“联合挂载”技术额外挂载一个“可写”层。
image layers
一般在一个应用镜像中,最底层的称为系统镜像,位于下层的也可以叫做父镜像。最上是可读写层,其下都是只读。如下图
假如要做一个nginx镜像,就需要在一个基础镜像上,这个镜像也必然是纯净的,最小化的系统镜像,或centos,debian,ubuntu等。
在这之上添加软件,构建过程等,并且这些是有层级关系的。系统镜像供给,配置编译等等,而这些都会被认为是一个层,在启动的时候这些都会被认为是一个层级。而bootfs在引导完成后就会被从内存中移除掉。而最上层writable才是可进行编辑可写,并且随着容器的删除而删除,也就是说可写层也没了。如上图。
其他参考:https://docs.docker.com/storage/storagedriver/#images-and-layers
aufs
镜像的分层构建和联合挂载依赖于中游文件系统支撑实现,早期的aufs( advanced multi-layered unification filesystem,翻译过来是多层统一的文件系统)就是被docker用于实现联合挂载的linux文件系统。aufs是对早期UnionFS的完全重构。
docker的分层镜像除了aufs,还支持btrfs,devicemapper和vfs等。在ubuntu系统下,docker默认使用ubuntu的aufs;而centos7,用的是devicemapper。而overlayfs在3.18版本开始已经被合并到linux内核。我们现在用的是overlayfs2
registry
镜像在本地build完成可以上传到registry上,而后在从registry拉取使用。如果本地有,就先用本地的,如果本地没有拉取registry上的。registry默认是dockerhub,如果需要指定自定义就需要重新修改配置,如果没有就默认dockerhub。docker本身是https,如果自建registry要使用http,就需要重新定义信任关系。
分类: sponsor registry:第三方的registry,供客户和社区使用 mirror registry: 第三方registry,如:aliyun加速镜像。 vendor registry: 服务商的registry,如: 红帽registry private registry: 自建registry。
registry分为两部分,仓库和索引共同组成,每个仓库有特定的docker镜像和不同的版本组成,同时分为顶层仓库和用户仓库两类,用户仓库名格式就是"用户名/仓库名"。而没个仓库可以包含多个tag,每个标签对应一个镜像。
index维护用户账号,镜像验证以及公共名称空间的信息,相当于registry提供一个完成用户认证等功能的检索接口。
registry中的镜像由开发人员制作,而后推送到公共或者是有的registry仓库中保存,以便于其他人员部署使用。如下:
通常,开发人员(从内网仓库或者dockerhub)拉取基础镜像,在原有的镜像之上添加一些应用,而后push到私有仓库中,而后使用的人进行拉取使用。其中,可进行环境变量配置,并且能够注入一些变量替换配置文件的。
而dockerhub可以将Docker Hub关联到GitHub帐户进行使用。如下图
github仓库可以与docker hub仓库建立关联关系,而docker hub可以持续监控github仓库,一旦添加新的内容,push到github后,github内容改变就进行重新build。