1、概括
Docker 的实现主要依赖 Linux的三大技术:Linux 命名空间、控制组 和 UnionFS
2、Linux 命名空间
命名空间(namespaces)是 Linux 为我们提供的用于分离进程树、网络接口、 挂载点以及进程间通信等资源的方法。在日常使用 Linux 或者 macOS 时, 我们并没有运行多个完全分离的服务器的需要,但是如果我们在服务器上启动了多个服务, 这些服务其实会相互影响的,每一个服务都能看到其他服务的进程,也可以访问宿主机器上的任意文件, 这是很多时候我们都不愿意看到的,我们更希望运行在同一台机器上的不同服务能做到完全隔离, 就像运行在多台不同的机器上一样。
Linux提供的命名空间机制包含clone_newcgroup、clone_newipc、clone_newnet、clone_newns、clone_newpid、clone_newuser、clone_newuts。
对于进程的隔离采用的是clone_newpid来实现的。
从主机的进程来看,1->29407->2554->5006,这其实是存在一个一颗进程树的
通过Linux的命名空间clone_newpid创建新进程,在底层的setNamespaces方法中传入进程、用户、网络等,创建新docker容器时把对应的隔离参数传递进去,从而实现了与宿主机、与各个容器的进程、用户、网络隔离。
类比: 这其实就和小区里不同楼层不同房间住着不同的业主是一个道理,早期在房子修建的时候, 开发商提供了不同栋的不同楼层的不同房间,业主们通过购房拥有了不同房间的入住权, 与每栋每楼层每房间都是独立的业主。
2.1、 网络
Docker 的容器通过 Linux 的命名空间创建了与宿主机隔离的网络命名空间
每一个使用 docker run 启动的容器其实都具有单独的网络命名空间, Docker 为我们提供了四种不同的网络模式,Host、Container、None 和 Bridge 模式。
3、CGroups 控制组
通过CGroups实现docker创建的 命名空间
对宿主机器的物理资源控制,比如当前空间占用多少CPU,多少内存等
每一个CGroup都可以为容器进行资源的分配,通过修改对应的参数就可以修改资源。下面这些参数是CGroups的子系统 对于docker来说,是通过参数调用子系统实现对资源的分配与控制,我们只需要关注如何配置参数即可,底层的大牛们早已写好,不用重复造轮子了哈。
- blkio:设置限制每个块设备的输入输出控制。例如:磁盘,光盘以及usb等等。
- cpu:使用调度程序为cgroup任务提供cpu的访问。
- cpuacct:产生cgroup 任务的cpu 资源报告
- cpuset:如果是多核心的 cpu,这个子系统会为 cgroup 任务分配单独的 cpu 和内存
- devices:允许或拒绝 cgroup 任务对设备的访问。
- freezer:暂停和恢复 cgroup 任务。
- memory:设置每个cgroup 的内存限制以及产生内存资源报告
- net_cls:标记每个网络包以供 cgroup 方便使用。
- ns:命名空间子系统。
- perf_event:增加了对每group 的监测跟踪的能力,可以监测属于某个特定的group 的所有线程以及运行在特定CPU上的线程
比如对于CPU的控制,在docker中使用cpu-shares参数指定容器所使用的CPU份额值(默认1024)
类比: 这就和房子装修是一个道理,整个房子买下来后,整体的面积已经固定, 我们可以去设计不同卧室的面积,比如整个房子100平米可用面积, 卧室空间默认是20平米,那么主卧参数100,次卧参数50,就表明了主卧面积是次卧的一倍, 主卧20平米,次卧10平米。
4、联合文件系统UnionFS(union file system)
把多个目录联合放在同一个目录下,而这些目录的物理位置是分开的。 在docker的镜像设计中,用户制作镜像的每一步操作就是多增加一个目录(docker中称之为层layer), 这个java程序1和java程序2所在的容器就引用相同的操作系统层、java环境层, 再结合应用程序层,启动docker容器时通过UnionFS把相关的层全放在一个目录里, 作为容器的根文件系统,而容器的启动就是可写层,来对docker镜像进行操作。
执行 docker run
命令的时候,就会在镜像的最上层添加一个可写的层,也就是容器层
容器和镜像的区别就像是对象和类信息一样的关系,一个镜像可以run多个容器
类比: 这种感觉就像修房子一样,一个房子里的20层里住着不同的业主, 他们有不同的装修风格、家电配置(这是最上层),但第二层(第1到19层住着一样的业主)、 第三层(一楼有一样的公共设施、环境)、最底层(相同的地基)都是一样的。