Dockerfile总结

是什么?

Dockerfile是一个包含所有可以用来组合镜像的命令的文本文档。可以通过dcoker build命令从Dockerfile构建镜像。

docker build -f /path/to/a/Dockerfile .

-f 指定Dockerfile的路径

指令

# Comment # 使用#标识注释

FROM:指定基础镜像

FROM必须为第一条指令。

FROM <image>[:<tag>] [AS <name>]: 设置基础镜像

  • 不指定标签时,默认使用latest版本

MAINTAINER:维护者信息

Syntax: MAINTAINER <name>

RUN:执行命令

用于指定 docker build 过程中运行的程序,其可以是任何命令

  • RUN命令支持两种格式:shell格式和exec格式。

  • 每条RUN指令将当前的镜像基础上的图层上执行指令,并提交为新的镜像,命令较长的时候可以使用\来换行。建议不要使用太多的RUN操作,考虑封装成shell脚本,或者用一条语句组装起来。所以正确写法应该是:

    RUN buildDeps='gcc libc6-dev make' \
             && apt-get update \
             && apt-get install -y $buildDeps \
             && wget -O redis.tar.gz "http://download.redis.io/releases/redis-3.2.5.tar.gz" \
             && mkdir -p /usr/src/redis \
             && rm -r /usr/src/redis \
             && apt-get purge -y --auto-remove $buildDeps
    
shell 格式

Syntax: RUN <command>

示例:

RUN echo '<h1>Hello, Docker!</h1>' > /usr/share/nginx/html/index.html
  • shell格式是以 /bin/sh -c 来运行它(推荐
    • 这意味着此进程在容器中的 PID 不为 1,不能接收 Unix 信号(比如kill信号),因此,当使用 docker stop <container> 命令停止容器时,此进程接收不到 SIGTERM 信号;
exec 格式

Syntax: RUN ["<executable", "<param1>", "<param2>"]

其中 <executable> 为要运行的命令

COPY:复制文本

复制本机文件到容器目录下

COPY <源路径>... <目标路径>
COPY ["<源路径1>",... "<目标路径>"]

<源路径> 指本机的src目录,可以是多个、以及使用通配符,通配符规则满足Go的filepath.Match 规则,如:

    COPY hom* /mydir/    
    COPY hom?.txt /mydir/

<目标路径>使用 COPY 指令,源文件的各种元数据都会保留。比如读、写、执行权限、文件变更时间等。

ADD:高级复制文件

复制本机文件到容器目录下,且支持从一个URL或一个tar文件拉取文件

  • tar文件会自动解压为目录
  • 原路径是URL时 ,下载后的文件权限自动设置为 600
COPY <源路径>... <目标路径>
COPY ["<源路径1>",... "<目标路径>"]
命令COPY和ADD命令有什么区别?

一般而言,虽然ADD并且COPY在功能上类似。唯一区别在于是否支持从远程URL获取资源。COPY指令只能从执行docker build所在的主机上读取资源并复制到镜像中。而ADD指令还支持通过URL从远程服务器读取资源并复制到镜像中。

满足同等功能的情况下,推荐使用COPY指令ADD指令更擅长读取本地tar文件并解压缩

CMD:容器启动命令

在运行镜像文件启动容器时,指定默认要运行的程序,且其运行结束后,容器也将终止。?

  • CMD指定的命令可被docker run时指定的cmd命令覆盖
  • 可以存在多个 CMD 指令,但仅有最后一个会生效

Syntax

  • CMD <command>
  • CMD ["<executable", "<param1>", "<param2>"]
  • CMD ["<param1>", "<param2>"]

前两种语法格式的意义同 RUN

第三种语法则用于 ENTRYPOINT 指令提供默认参数

ENTRYPOINT:入口点

同CMD,指定容器启动程序及参数。

  • CMD 不同的是,由 ENTRYPOINT 启动的程序不会被 docker run 命令行指定的参数所覆盖,而且,这些命令行参数会被当做参数传递给 ENTRYPOINT 指定的程序
  • docker run 命令的 --entrypoint 选项的参数可覆盖 ENTRYPOINT 指令指定的程序
  • 可以存在多个 ENTRYPOINT 指令,但仅有最后一个会生效

Syntax:

  • ENTRYPOINT <command>
  • ENTRYPOINT ["<executable>", "<param1>", "<param2>"]
命令CMD和ENTERYPOINT的关系
  1. Dockerfile必须指定至少一个CMDENTERYPOINT命令

  2. ENTERYPOINT的优先级高于CMD,如果二者同时存在,且均使用数组的方式,那么CMD的参数会在后面追加到ENTERYPOINT命令(详见

  3. 有多个时都只执行最后一个

ENV:设置环境变量

Syntax:ENV <key> <value> \ <key>=<value>

  • 在其他指令中可以直接引用ENV设置的环境变量。

  • 可以使用docker run --env <key>=<value>修改环境变量

ARG:构建参数

Syntax:ARG <name>[=<default value>] : docker file中的变量

与ENV不同的是,容器运行时不会存在这些环境变量。
可以用 docker build --build-arg <参数名>=<值> 来覆盖。

VOLUME:定义匿名卷

在制作镜像时挂载卷。会在宿主机上自动生成一个对应的共享目录。

  • 一个卷可以存在于一个或多个容器的指定目录,该目录可以绕过联合文件系统
  • 修改卷后立即生效
  • 卷的修改不影响镜像

Syntax:VOLUME ["/path"]

EXPOSE:暴露端口

容器监听的端口和协议,供容器外部连接使用。默认使用TCP

  • 运行容器时可以通过制定- p重写该配置

    docker run -p 80:80/tcp -p 80:80/udp ...
    

Syntax:EXPOSE <port> [<port>/<protocol>...]

WORKDIR:指定工作目录

为后续命令指定工作目录

  • 注意再次指定目录时如果是相对路径要基于之前的命令

Syntax:WORKDIR <工作目录路径>

USER:指定当前用户

指定容器运行时的用户名或UID,后续的RUN也会使用指定的用户。

  • 这个用户必须是事先建立好的,否则无法切换。

Syntax:USER <user>[:<group>] / <UID>[:<GID>]

HEALTHCHECK:健康检查

设置检查容器健康状况的命令

HEALTHCHECK [选项] CMD <命令>
HEALTHCHECK NONE :如果基础镜像有健康检查指令,使用这行可以屏蔽掉其健康检查指令

HEALTHCHECK 支持下列选项:

  • --interval=<间隔> :两次健康检查的间隔,默认为 30 秒;

  • --timeout=<时长> :健康检查命令运行超时时间,如果超过这个时间,本次健康检查就被视为失败,默认 30 秒;

  • --retries=<次数> :当连续失败指定次数后,则将容器状态视为 unhealthy ,默认 3次。

  • command 的 exit status 表明容器的健康状态

    • 0: success
    • 1: unhealthy
    • 2: reserved - do not use this exit code (可以自己定义)
  • 例子(\ 表示换行)

HEALTHCHECK --interval=5m --timeout=3s \
CMD curl -f http://localhost/ || exit 1

执行exit可使shell以指定的状态值退出。

LABEL:镜像标签

LABEL <key>=<value> <key>=<value> ... : 镜像标签,方便使用

ONBUILD:定义触发器

Syntax

  • ONBUILD <INSTRUCTION>

Dockerfile作为镜像文件,会作为base image被另一个Dockerfile使用,来构建新的镜像文件。在新镜像文件执行FROM时,会触发base image的Dockerfile中定义的触发器

  • 尽管任何指令都可以注册成为触发器指令,但 ONBUILD 不能自我嵌套,且不会触发 FROMMAINTAINER 指令
  • 使用包含 ONBUILD 指令的 Dockerfile 构建的镜像应该使用特殊的标签,例如 ruby:2.0-onbuild
  • ONBUILD 指令中使用 ADDCOPY 指令应该格外小心,因为新构建过程的上下文在缺少指定原文件时会失败

参考:

https://www.jianshu.com/p/168fbb97b447

https://www.jianshu.com/p/ed4818838385

https://www.jianshu.com/p/c39e32396319

https://docs.docker.com/engine/reference/builder/

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值