docker学习 - docker run

简介: #docker run流程 ## 创建容器 - 通过用户指定的镜像名和tag,在TagStore中查找image_id,获取image对象(本地的image json文件里有镜像信息) - 检查镜像layer数(不超过127),镜像层数太多会造成性能问题 - 将runconfig.Config和image.Config合并 - 创建{Container.ID}-init和Containe

docker run流程

创建容器

  • 通过用户指定的镜像名和tag,在TagStore中查找image_id,获取image对象(本地的image json文件里有镜像信息)
  • 检查镜像layer数(不超过127),镜像层数太多会造成性能问题
  • 将runconfig.Config和image.Config合并
  • 创建{Container.ID}-init和Container.ID镜像的目录,在init layer创建.dockerinit、/etc/hosts、/etc/hostname等, Container.ID镜像是read-write layer
  • 将Container对象持久化到path.Join(Container.ID, “config.json”)
  • 在Daemon.idIndex中注册Container.ID,在Daemon.contStore中记录Container.ID和Container对象的映射关系

启动容器

  • 通过Container.ID从Daemon.contStore中获取Container对象
  • 配置容器的dns地址/etc/resolv.conf
  • 将所有祖先镜像挂载到path.Join(graphdriver.root, “mnt”, Container.ID)
  • 初始化容器的hosts文件/etc/hosts
  • 检查主机是否开启cgroup内存限制、swap内存限制、ipv4转发
  • 将容器内挂在目录和宿主机目录的映射关系存入container.Volume
  • 将容器的link信息存入graphdb中,基于sqllite的图模型的数据库
  • 通过iptables开启link容器间的通信,并env化
  • 获取容器运行的当前目录,获取用户指定的环境变量
  • 构建execdriver的Command对象,包括进程命令、Network、Mount、Resources、WorkingDir,用于容器的启动和配置
  • 将Command对象持久化到path.Join(config.root, “execdriver/native/container.json”)
  • 通过execdriver.Run启动Command对象

启动dockerinit

dockerinit是daemon启动容器运行的第一个进程,类似linux的init进程
初始化容器的Network资源、Mount资源、设置用户、设置环境变量等在daemon进程中做不到事情
Daemon执行流程

  • 创建syncPipe用于跨namespace的通信
  • execdriver.Run创建一个exec.Cmd对象来执行dockerinit命令
  • exec.Cmd.Args代表dockerinit的执行参数,native表示execdriver类型,pipe表示同步管道的文件描述符,root表示容器- 配置文件container.json和state.json所在目录,args表示用户指定的命令
  • Exec.Cmd.SysProcAttr携带需要为进程创建新namespace参数Cloneflags,包括NEWNS、NEWUTS、NEWIPC、NEWPID、NEWNET
  • 调用exec.Cmd.Start()启动dockerinit进程
  • 调用namespaces.SetupCgroups为dockerinit配置cgroup(cpu、iops、memory、freezer)
  • 调用namespaces.InitializeNetworking为dockerinit创建网络栈
  • 调用syncPipe.SendToChild(networkState)将需要dockerinit完成的剩余网络配置发给dockerinit
  • 调用syncPipe.ReadFromChild与dockerinit同步

Daemon执行流程

  • 创建syncPipe用于跨namespace的通信
  • execdriver.Run创建一个exec.Cmd对象来执行dockerinit命令
  • exec.Cmd.Args代表dockerinit的执行参数,native表示execdriver类型,pipe表示同步管道的文件描述符,root表示容器- 配置文件container.json和state.json所在目录,args表示用户指定的命令
  • Exec.Cmd.SysProcAttr携带需要为进程创建新namespace参数Cloneflags,包括NEWNS、NEWUTS、NEWIPC、NEWPID、NEWNET
  • 调用exec.Cmd.Start()启动dockerinit进程
  • 调用namespaces.SetupCgroups为dockerinit配置cgroup(cpu、iops、memory、freezer)
  • 调用namespaces.InitializeNetworking为dockerinit创建网络栈
  • 调用syncPipe.SendToChild(networkState)将需要dockerinit完成的剩余网络配置发给dockerinit
  • 调用syncPipe.ReadFromChild与dockerinit同步

Dockerinit执行流程

  • 从参数中读取root配置文件所在目录
  • 从path.Join(root, “container.json”)中读取daemon传过来的execdriver.Command对象,获取容器的配置信息
  • 调用mount.InitializeMountNamespace完成挂载资源的初始化,包括rootfs根文件系统,挂载点Volume,设备文件
  • 调用namespaces.FinalizeNamespace完成剩余的配置,包括关闭除0/1/2以外的文件句柄,为容器创建新的用户ID、组ID,切换到工作目录
  • 调用syscall.Exec将容器主进程的执行权交给用户程序
相关文章
|
19天前
|
存储 关系型数据库 MySQL
|
27天前
|
存储 Ubuntu Linux
学习docker
学习docker
30 1
|
29天前
|
NoSQL Linux Redis
Docker学习二(Centos):Docker安装并运行redis(成功运行)
这篇文章介绍了在CentOS系统上使用Docker安装并运行Redis数据库的详细步骤,包括拉取Redis镜像、创建挂载目录、下载配置文件、修改配置以及使用Docker命令运行Redis容器,并检查运行状态和使用Navicat连接Redis。
202 3
|
1月前
|
运维 Kubernetes 开发者
Docker Swarm学习
【10月更文挑战第5天】
33 3
|
1月前
|
Kubernetes Linux 持续交付
docker容器学习
【10月更文挑战第1天】
35 1
|
2月前
|
存储 Ubuntu Docker
Docker学习
Docker学习
59 4
|
1月前
|
Linux 应用服务中间件 Shell
docker学习--docker容器镜像常用命令大全(简)
本文档详细介绍了Docker中的镜像命令与容器管理命令。镜像命令部分涵盖了镜像搜索、下载、上传等操作;容器管理命令则包括了容器的创建、启动、停止、删除及日志查看等功能。通过具体示例,帮助用户更好地理解和使用Docker相关命令。
140 0
|
1月前
|
Shell 应用服务中间件 nginx
docker学习--最详细的docker run 各子命令解释与应用
`docker run` 是 Docker 中用于启动容器的基本命令。常用子命令包括 `-i`(交互模式)、`-t`(分配终端)、`-d`(后台运行)、`-p`(端口映射)、`--name`(指定容器名)。例如,`docker run -it nginx:1.20 /bin/bash` 可以创建并进入交互式容器。使用 `-d` 可在后台运行容器,`-p` 可将容器端口映射到主机端口,`--name` 则用于自定义容器名称以便管理。
131 0
|
2月前
|
Docker 容器
docker run
【9月更文挑战第08天】
68 1
|
2月前
|
关系型数据库 MySQL 数据库
docker启动mysql多实例连接报错Can’t connect to local MySQL server through socket ‘/var/run/mysqld/mysqld.sock’
docker启动mysql多实例连接报错Can’t connect to local MySQL server through socket ‘/var/run/mysqld/mysqld.sock’
172 0