
3.2 开放容器倡议
随着容器在整个行业中的不断普及,显然需要标准和规范来确保容器运动的成功。开放容器倡议(OCI)是一个成立于2015年的开源项目,旨在围绕容器的规范进行合作。这个倡议的著名创始者包括Docker和CoreOS,前者向OCI捐赠了runc,后者则用rkt推动了容器运行时间的发展。
OCI包括三个规范:OCI运行时规范、OCI镜像规范和OCI分发规范。这些规范实现了围绕容器和容器平台(如Kubernetes)的开发和创新。此外,OCI的目的是允许最终用户以可移植和可互操作的方式使用容器,使他们在必要时能够更容易地在产品和解决方案之间移动。
在以下小节中,我们将探讨容器运行时和镜像的规范。我们不会深入研究分发规范,因为它涉及容器镜像注册表。
3.2.1 OCI运行时规范
OCI运行时规范决定了如何以兼容OCI的方式实例化和运行容器。首先,该规范描述了一个容器的配置模式。该模式包括诸如容器的根文件系统、运行的命令、环境变量、使用的用户和组、资源限制等信息。下面是一个从OCI运行时规范中获得的容器配置文件的片段。

运行时规范还确定了容器运行时必须支持的操作,包括create、start、kill、delete和state(提供关于容器状态的信息)。除了操作之外,运行时规范还描述了容器的生命周期,以及它如何通过不同的阶段进行发展。生命周期阶段是:(1)creating,当容器运行时正在创建容器时,它是活跃的;(2)created,当运行时完成create操作时;(3)running,当容器进程开始并运行时;(4)stopped,当容器进程结束时。
OCI项目还容纳了runc,这是一个低级别的容器运行时,实现了OCI运行时规范。其他更高级别的容器运行时(如Docker、containerd和CRI-O)都使用runc来根据OCI规范生成容器,如图3-1所示。利用runc使容器运行时能够专注于更高层次的功能,如拉取镜像、配置网络、处理存储等,同时符合OCI运行时规范。

图3-1:Docker引擎、containerd和其他运行时根据OCI规范使用runc来生成容器
3.2.2 OCI镜像规范
OCI镜像规范的重点是容器镜像。该规范定义了一个清单、一个可选的镜像索引、一组文件系统层和一个配置。镜像清单描述了该镜像。它包括一个指向镜像配置的指针,一个镜像层的列表,以及一个可选的注释图。下面是一个从OCI图像规范中获得的清单示例。


镜像索引是一个顶层清单,能够创建多平台的容器镜像。镜像索引包含指向每个特定平台清单的指针。下面是一个从规范中获得的索引的示例。请注意该索引如何指向两个不同的清单,一个用于ppc64le/linux,另一个用于amd64/linux。

每个OCI镜像声明文件都引用了一个容器镜像配置。该配置包括镜像的入口点、命令、工作目录、环境变量等。容器运行时在从镜像实例化为容器时使用该配置。下面的片段显示了一个容器镜像的配置,为了简洁起见,删除了一些字段。


OCI镜像规范还描述了如何创建和管理容器镜像层。镜像本质上是包括文件和目录的TAR档案。该规范为镜像层定义了不同的媒体类型,包括未压缩的镜像层、已压缩的镜像层和不可分配的镜像层。每层都是由一个摘要唯一识别的,通常是该层内容的SHA256总和。正如我们之前讨论的,容器镜像声明文件引用了一个或多个层。这些引用使用SHA256摘要来指向一个特定的层。最终的容器镜像文件系统是应用声明文件中所列举各层的结果。
OCI镜像规范是至关重要的,因为它确保了容器图像在不同的工具和基于容器的平台上是可移植的。该规范使不同的镜像构建工具得以开发,如用于用户空间容器构建的kaniko和Buildah,用于基于Java的容器的Jib,以及用于简化和自动化构建的Cloud Native Buildpacks(我们将在第15章探讨其中的一些工具)。总的来说,该规范确保Kubernetes可以运行容器镜像,而不管用于构建容器的工具是什么。