如何使用Dockerfile构建Docker镜像

时间:2020-03-05 15:25:17  来源:igfitidea点击:

Docker镜像是Docker容器的蓝图,其中包含应用程序以及运行该应用程序所需的一切。
容器是镜像的运行时实例。

在本教程中,我们将解释什么是Dockerfile,如何创建Dockerfile以及如何使用Dockerfile构建Docker镜像。

什么是Dockerfile

Dockerfile是一个文本文件,其中包含用户可以在命令行上运行以创建镜像的所有命令。
它包含Docker生成镜像所需的所有指令。

Docker镜像由一系列文件系统层组成,这些文件系统层代表镜像的Dockerfile中的指令,该指令构成了可执行的软件应用程序。

Docker文件采用以下形式:

# Comment
INSTRUCTION arguments

'INSTRUCTION'不区分大小写,但是约定是使用UPPERCASE作为其名称。

以下是对一些最常用的Dockerfile指令的简短描述的列表:

  • ARG-此指令使我们可以定义在构建时可以传递的变量。我们也可以设置默认值。
  • FROM-用于构建新图像的基本图像。该指令必须是Dockerfile中的第一条非注释指令。该规则的唯一例外是当我们想在'FROM'参数中使用变量时。在这种情况下,“ FROM”之前可以有一个或者多个“ ARG”指令。
  • LABEL-用于向图像添加元数据,例如描述,版本,作者等。我们可以指定多个“ LABEL”,并且每个“ LABEL”指令都是一个键值对。
  • RUN-该指令中指定的命令将在构建过程中执行。每条“ RUN”指令都会在当前图像的顶部创建一个新层。
  • ADD-用于将文件和目录从指定源复制到Docker镜像上的指定目标。源可以是本地文件或者目录,也可以是URL。如果源是本地tar归档文件,那么它将自动解压缩到Docker镜像中。
  • COPY-与“ ADD”相似,但源只能是本地文件或者目录。
  • ENV-此指令可让我们定义环境变量。
  • CMD-用于指定运行容器时将执行的命令。我们只能在Dockerfile中使用一个'CMD'指令。
  • ENTRYPOINT-与“ CMD”类似,此指令定义运行容器时将执行的命令。
  • WORKDIR-该指令为'RUN','CMD','ENTRYPOINT','COPY'和'ADD'指令设置当前工作目录。
  • USER-设置用户名或者“ UID”,以在运行以下任何“ RUN”,“ CMD”,“ ENTRYPOINT”,“ COPY”和“ ADD”指令时使用。
  • VOLUME-使我们可以将主机目录挂载到容器。
  • EXPOSE-用于指定容器在运行时侦听的端口。

要从文件和目录中排除文件和目录,请在上下文目录中创建一个“ .dockerignore”文件。
“ .dockerignore”的语法类似于Git的“ .gitignore”文件之一。

有关Dockerfile指令的完整参考和详细说明,请参见官方Dockerfile参考页面。

创建一个Dockerfile

创建Docker镜像时,最常见的情况是从注册表(通常是从Docker Hub)中提取现有镜像,并指定要在基础镜像上进行的更改。
创建Docker镜像时,最常用的基础镜像是Alpine,因为它很小并且经过优化,可以在内存中运行。

Docker Hub是基于云的注册表服务,除其他功能外,还用于将Docker镜像保存在公共或者私有存储库中。

在此示例中,我们将为Redis服务器创建一个Docker镜像。
我们将使用最新的ubuntu 18.04作为基本图片。

首先,创建一个目录,其中将包含Dockerfile和所有必需的文件:

mkdir ~/redis_docker

导航到目录并创建以下Dockerfile:

cd ~/redis_dockernano Dockerfile

Docker文件

FROM ubuntu:18.04
RUN apt-get update && \
    apt-get install -y redis-server && \
    apt-get clean
EXPOSE 6379
CMD ["redis-server", "--protected-mode no"]

让我们解释一下Dockerfile中每一行的含义:

  • 在“ 1”行上,我们定义了基本图像。
  • 从“ 3”行开始的“ RUN”指令将更新apt索引,安装“ redis-server”软件包并清理apt缓存。说明中使用的命令与在Ubuntu服务器上安装Redis所使用的命令相同。
  • “ EXPOSE”指令定义Redis服务器侦听的端口。
  • 在最后一行中,我们使用“ CMD”指令设置将在容器运行时执行的默认命令。

保存文件并关闭编辑器。

构建镜像

下一步是构建镜像。
为此,请从Dockerfile所在的目录中运行以下命令:

docker build -t theitroad/redis .

选项“ -t”以“用户名/图像名:标记”格式指定图像名称以及用户名和标记(可选)。

构建过程的输出将类似于以下内容:

Sending build context to Docker daemon  3.584kB
Step 1/4 : FROM ubuntu:18.04
 ---> 7698f282e524
Step 2/4 : RUN apt-get update &&     apt-get install -y gosu redis-server &&     apt-get clean
 ---> Running in e80d4dd69263
...
Removing intermediate container e80d4dd69263
 ---> e19fb7653fca
Step 3/4 : EXPOSE 6379
 ---> Running in 8b2a45f457cc
Removing intermediate container 8b2a45f457cc
 ---> 13b92565c201
Step 4/4 : CMD ["redis-server", "--protected-mode no"]
 ---> Running in a67ec50c7048
Removing intermediate container a67ec50c7048
 ---> d8acc14d9b6b
Successfully built d8acc14d9b6b
Successfully tagged theitroad/redis:latest

构建过程完成后,新图像将在图像列表中列出:

docker image ls
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
theitroad/redis      latest              d8acc14d9b6b        4 minutes ago       100MB
ubuntu              18.04               7698f282e524        5 days ago          69.9MB

如果要将镜像推送到Docker Hub,请参阅将Docker容器镜像推送到Docker Hub。

运行容器

现在已经创建了镜像,我们可以通过运行以下命令从中运行一个容器:

docker run -d -p 6379:6379 --name redis theitroad/redis

'-d'选项告诉Docker以分离模式运行容器,'-p 6379:6379'选项会将端口6379发布到主机,而'--name redis'选项指定容器名称。
最后一个参数“ theitroad/redis”是镜像的名称,用于运行容器。

容器启动时,使用以下命令列出所有正在运行的容器:

docker container ls
CONTAINER ID        IMAGE                   COMMAND                  CREATED             STATUS              PORTS                    NAMES
6b7d424cd915        theitroad/redis:v0.0.1   "redis-server '--pro…"   5 minutes ago       Up 5 minutes        0.0.0.0:6379->6379/tcp   redis

要验证一切正常,应使用“ redis-cli”连接到Docker容器:

redis-cli ping

Redis服务器应回复'PONG'响应。