docker 18版本_docker 18版本

Docker的核心知识只有3个:镜像、容器、仓库



掌握了这3个铁三角,也就掌握了Docker的核心,看似高深,读到最后它们三兄弟也就豪横不起来了。

Docker 镜像 Image

Docker镜像就相当于是一个 root 文件系统。比如官方镜像 ubuntu:18.04 就包含了完整的一套Ubuntu 18.04 最小系统的 root 文件系统。

Docker 镜像是一个特殊的文件系统,除了提供容器运行时所需的程序、库、资源、配置等文件外,还包含了一些为运行时准备的一些配置参数(如匿名卷、环境变量、用户等)。镜像不包含任何动态数据,其内容在构建之后也不会被改变。




docker 18版本_文件系统_02

Docker镜像的分层构建示意图



镜像构建时,采用分层存储,会一层层构建,前一层是后一层的基础。每一层构建完就不会再发生改变,后一层上的任何改变只发生在自己这一层。

举例解析(参照上图)

  1. 1层的centos是独立的镜像A
  2. 在A镜像的基础之上又要安装个JDK,因此叠加了2层镜像,那么1+2就形成了新的镜像B
  3. 在B镜像的基础之上又要安装个Tomcat,因此叠加了3层镜像,那么1+2+3就形成了新的镜像C
  4. 以此类推,所以镜像构建就像搭积木一样,底层是上层的基础

分层存储的特征还使得镜像的复用、定制变得更为容易。甚至可以用之前构建好的镜像作为基础层,然后进一步添加新的层,以定制自己所需的内容,构建新的镜像。

举例解析(参照上图)

  1. 将第1层的centos拿出来,再叠加一个nodejs,那么就形成了nodjs的运行环境镜像
  2. 将第1层的centos和第2层的jdk拿出来,再叠加上一个ActiveMQ镜像,就形成了全新的消息队列镜像。
  3. 这就是镜像分层的复用能力

Docker 容器 Container

镜像和容器的关系,就像是面向对象程序设计中的类和实例 一样,镜像是静态的定义,容器是镜像运行时的实体。容器可以被创建、启动、停止、删除等。




docker 18版本_Docker_03

镜像和容器的关系,就好像类和实例之间的关系



如上图所示:一个镜像类可以new出来多个容器实例,容器实例可以创建、可以销毁。




docker 18版本_文件系统_04

容器的隔离运行机制,在沙箱里运行



容器的实质是进程,但与直接在宿主执行的进程不同,容器进程运行于属于自己的独立的命名空间(沙箱)。因此容器可以拥有自己的 root 文件系统、自己的网络配置、自己的进程空间,甚至自己的用户 ID 空间,达到极强的隔离性。

容器内的进程是运行在一个隔离的环境里,使用起来,就好像是在一个独立于宿主的系统下操作一样。这种特性使得容器封装的应用比直接在宿主运行更加安全。

Docker 仓库 Repository

一个集中的存储、分发镜像的服务。




docker 18版本_Docker_05

Docker仓库的存储结构示意图



一个 Docker Registry(私服) 中可以包含多个仓库Repository;每个仓库可以包含多个标签Tag;每个标签对应一个镜像。

私服的概念在下一篇文章讲解,现在可以先不用理解

一个仓库会包含同一个软件不同版本的镜像,而标签就常用于对应该软件的各个版本。我们可以通过 : 的格式来指定具体是这个软件哪个版本的镜像。如果不给出标签,将以 latest 作为默认标签

举例解析(参照上图)

  1. jdk、kafka、mysql都存储在不同的仓库(Repository)中
  2. 每个仓库都有不同的版本(TAG),一个TAG对应一个真实的镜像
  3. 例如JDK有7、8版本,latest代表最新版本,对应的是3个镜像。
  4. 例如MySQL有6.0.1和7.0.9两个版本,对应的也是2个镜像。



docker 18版本_docker 18版本_06

Docker仓库-实例



举例解析(参照上图: 真实服务器截图)

使用docker images命令可以列出服务器上的所有镜像信息

java仓库有两个TAG,分别是7和8。代表着java7、java8两个版本的JDK镜像。

IMAGE_ID代表镜像的唯一ID,我们可以使用此ID将镜像从我们的本地仓库中删除(docker rmi IMAGE_ID命令)。

CREATED代表镜像的创建时间是在3年前

SIZE代表镜像的大小