美文网首页
Dockerfile

Dockerfile

作者: 麟之趾a | 来源:发表于2020-07-15 16:44 被阅读0次

    Dockerfile

    dockerfile是个纯文本文件,里面包含了dockerfile支持的指令
    dockerfile的格式
    1.注释信息
    2.指令+参数
    指令不区分大小写,一般使用大写。指令是按照顺序执行的
    第一个非注释行,是FROM用来说明此镜像,是基于哪个基础镜像做的

    docker build 命令

    docker image build -h
    -t --tag: 给做的镜像打个标签
    -q --quiet 不显示做镜像的过程
    --rm: 做镜像过程中,自动启动的工作容器。是否自动删除。默认为true
    

    Dokefile的说明

    dockerfile中的每一条指令,都是单一镜像层。
    容器化使用环境变量来配置程序的配置文件,但传统的应用程序不支持环境变量的方式,为此在容器启动之前使用脚本,把环境变量注入应用的配置文件中,这个脚本通常是entrypoint.sh脚本(名称通常也是这个)

    环境变量的使用

    1.在构建dockefile中使用
    2.在镜像运行为容器中使用

    ${varialbe:-world} 如果变量未设定,或者值为空,就给变量world值,否则会返回变量自身的值
    ${varialbe:+world}如果变量设定,有值。就返回world,如果变量为空,就返回空。
    .dockerignore  指docker build过程中,忽略这个文件以及忽略这个文件所包含的文件
    

    Dockerfile指令

    FROM

    FROM <respority>:<tag>
    FROM <responrity>@<digest> //digest为镜像的唯一标识
    

    MAINTANIER

    AINTANIER <author' s detail>
    例: MAINTANIER  "magedu"
    让dockerfile 制作者提供个人信息,推荐放在FROM后面,现以废弃,但仍可以使用
    

    LABEL

    LABEL <key>=<value>  <key>=<value>
    MAINTANER 替代指令,MAINTANER是个key/value 指令,只支持作者的一个key信息。LABEL可以自定义key值
    

    COPY

    用于从Docker主机复制文件至创建的新映像的文件
    语法
    COPY <src>  .... <dest>
    COPY ["<src>",...."<dest>"]
    <src>:要复制的源文件或目录,支持使用通配符
    <dest>: 目标路径,即正在创建的image的文件
    系统路径: 建议<dest>使用绝对路径,否则COPY指定的规则以WORKDIR为起始路径
    注意: 在路径中有空白字符时,通常使用第二种格式
    文件复制准则
    <src>必须是build 上下文中的路径,但不能其父目录的文件
    如果<src>是目录,则内部文件或子目录会被递归复制,但<src>自身不会被复制,如果指定了多个<src>,或者在<src>中使用了通配符,则<dest>必须是一个目录,且必须以/结尾。如果<dest>事先不存在,它将会被自动创建,包括父目录的路径
    

    ADD

    ADD 指令类似于COPY指令,ADD支持TAR和URL路径
    语法
    ADD <src> .... <dest>
    ADD ["<src>",...,"<dest>"]
    操作准则:
    同COPY指令
    如果<src>为URL,且<dest>不以/结尾,则<src> 指定的文件被下载并直接创建为<dest>,如果<dest>以/结尾,则文件名URL指定的文件被直接下载并保存为<dest>/filename,如果<src>是一个本地的文件系统上的压缩格式的tar文件,它将被展开为一个目录。其行为类似"tar -x"命令,然而通过URL获取的tar文件将不会自动展开。
    如果<src>有多个,或其间接或直接使用了通配符,则<dest>必须以/结尾的目录路径,如果<dest>不以/结尾,则被视为一个普通文件,<src>的内容将直接写入<dest>
    ADD 也能解压 tgz 的包
    

    WORKDIR

    设置Dockerfile中所有的RUN,CMD,ENTRYPOINT,COPY和ADD和设定工作目录
    WORKDIR <dirpath>
    在Dockerfile 文件中,WORKDIR指令可出现多次,其路径也可以为相对路径,不过是相对此前一个WORKDIR指令的路径
    另外,WORKDIR也可以调用由ENV指定定义的变量
    例如: WORKDIR /var/log
    WORKDIR $STATEPATH
    

    VOLUME

    用于在image中创建一个挂载点目录,以挂载Dockerhost上的卷或其他容器的卷
    syntax:
    VOLUME <mountpoint>
    VOLUME ["<mountpoint>"]
    注意: 此处只标记为它为存储卷,如果使用docker run时,没有用-v 来定义。此处为docker 管理的卷,即docker自动创建这个目录做映射关系。如果需要自定义路径,还需要-v 指定
    Dokcer 挂载卷,如果挂载点有数据,会先把数据复制到存储卷上,然后再挂载,该挂载还是会隐藏原先的数据
    

    EXPOSE

    用于为容器打开指定要监听的端口,以实现与外部通信
    EXPOSE <port>/<protocol> <port>/<protocol>
    EXPOSE 11211/tcp  11211/udp
    在容器运行时,需要-P(大写)要暴露容器所有监听的端口,将其映射为动态端口.
    -p(小写) 自己指定映射的端口和容器端口
    

    ENV

    此变量在docker build 过程中生效,用于为镜像定义所需的环境变量,并可被Dockerfile文件中位于其他指令如ADD,COPY所调用
    调用格式为:$variable_name 或 ${variable_name}
    syntax:
    ENV <key> <value>
    ENV <key>=<value> <key>=<value>
    第一种格式中: <key>之后的所有内容均会被视为<value>的组成部分,因此一次只能设置一个变量
    第二种格式中: 可用设置多个变量,每个变量为一个"<key>=<value>" 的键值对,如果<value>中有空格,可以使反斜线(\)进行转义,也可以对<value>加引号进行标识,另外反斜线也可用于续行
    定义多个变量,建议使用第二种方式,以便在同一层完成所有功能
    

    ARG

    定义一个变量在dockefile中,在build-time可以使用--build-arg <varname>=<value> 来传值,ARG变量的引用方式是相似的语法
    syntax:
    ARG <name>[=<default_value>]
    default_value:也可以没有
    

    RUN,CMD,ENTRYPOINT 区别

    build 阶段使用RUN运行shell命令,构建目标镜像在build过程中本身,会启动一个容器,是在容器中运行RUN 指令的命令
    CMD和ENTRYPOINT 是docker run中,容器默认运行的命令
    假: 只有CMD指令,且CMD有多个,最后一个CMD生效
    只有ENTRYPOINT,且有多个。最后一个ENTRYPOINT,生效
    如果CMD和ENTRYPOINT同时存在CMD做为参数传递给ENTRYPOINT
    

    进程的补充

    我们平时通过ssh连进去,运行一个tail -f 命令,当我们ssh断了,里面的shell(/bin/bash)和tail进程也就中断了。我们在命令行界面运行的任何命令都是shell的子进程
    守护进程: nohup tail -f **.log &
    &: 意味着把进程,运行为后台
    nohup: 意味着把当前进程,剥离当前终端。即shell停止,这个进程也不会停止。此为守护进程的意义和价值
    ls * #/ * 并不是ls的参数,而是有shell解析完成后传递给ls的
    crontab 运行我们的命令使用绝对路径,此命令为init的子进程,而不是shell创建的
    进程有两种运行方式,一种由init运行,一种由shell运行

    RUN

    用于指定docker build过程中运行的程序,其可以是任何一个命令(上层镜像必须存在此命令)
    syntax
    RUN <command>
    RUN ["<executable>","<param1>","<param2>]"
    第一种命令格式,<command>通常是一个shell命令,且以"/bin/sh -c"来运行他,意味着此进程,在容器的PID不为1,不能接受unix信号,因此使用docker stop <container> 命令停止容器,此进程接受不到SIGTERM信号
    第二种语法格式的参数,是一个json格式的数组,其中<executable>为要运行的命令,后面的<param1>为传递命令的选项或参数,然而此种格式指定的命令不会以"/bin/sh -c"来发起,因此常见的shell操作,如变量的替换以及通配符(?*),输入输出重定向,管道符将不会进行,如果要运行命令的命令,依赖此shell的化
    RUN ["/bin/bash","-c","<executable>","<param1>"]
    只要带上[],命令都不会以shell子进程运行,除非明确指定
    

    CMD

    类似于RUN指令,CMD运行于docker run 中,可以有多个,最后一个生效。CMD指定的命令就可以被docker run的命令所覆盖
    syntax
    CMD <command>
    CMD ["<executable>","<param1>","<param2>"] 
    CMD ["<param1>","<param2>"]
    前两种语法意义与RUN相同,最后一种为ENTRYPOINT提供的参数
    docker run --name web1 -it --rm php-httpd:v0.2 /bin/bash
    让/bin/bash 覆盖原先的CMD命令
    

    ENTRYPOINT

    与CMD命令差不多,docker run后面的命令,会当作参数传给ENTRYPOINT命令
    如果想ENTRYPOINT被覆盖,在docker run 中加入参数--entrypoint
    docker run --name web --it --rm --entrypoint "/bin/bash" php-httpd:v0.3
    一般: ENTRYPOINT ["/bin/entrypoint.sh"] 运行一个脚本,这个脚本用来传递环境变量来设置配置文件
    vim entrypoint.sh //这个脚本一定有基础镜像支持
    #!/bin/bash
    server_name=${SERVER_NAME:-localhost}
    doc_root=${DOC_ROOT:-/var/www/html/}
    cat > /etc/httpd/conf.d/myweb.conf  <<EOF
    <VirtualHost  *:80>
      ServerName  "$server_name"
      DocumentRoot "$doc_root"
     <Directory "$doc_root">
        Options none
        Allow Override none
        Require all granted
    </Directory>
    </VirtualHost>
    EOF
    exec "$@"
    --------------------------------------------------------------------------------------------------------------------------
    $@为CMD传递过来的参数,$@ 代表所有的参数。exec为目标进程替代当前进程,希望此进程在容器是PID为1的进程
    让entrypoint.sh脚本有执行权限,并且把这个脚本传到新做的镜像里面去
    docker container run --name myweb --rm -e SERVER_name=magedu php-httpd:v0.4
    使用-e参数往里面传递参数,传进去的任何变量都可以在容器中看到,内部没定义也可以看到。也可以用printenv传递命令
    

    USER

    用于指定运行image或运行Dockerfile中任何RUN,CMD和ENTRYPOINT指令,指定的程序时的用户名或UID
    默认情况下,container的运行的身份为root用户
    syntax
    USER <UID>|<UserName>
    需要注意的是,<UID>可以为任意数字,但实践中,其必须为/etc/passwd的有效UID,否则docker run将运行失效
    

    HEALTHCHECK

    健康状态检测
    一般情况下,容器是否存活,是看容器内的这个进程是否存在。如果进程依然存在,但已停止工作,会出现问题HEALTHCHECK是一个用命令探测,容器内的进程是否正常工作,如果不正常,则重启容器。
    注意:此命令是在容器内执行,因此容器内必须支持此命令用来排查
    syntax
    HEALTCHECK [options]  CMD command
    HEALTCHECK none 不做健康状态检查
    CMD是固定字符串
    [options]
    --interval=DURATION(default 30s) 发起请求的间隔时间
    --timeout=DURATION(default 30s)等待响应结果的超时时间
    --start-period=DURATION(default 0s) 开始检测之前,等待进程起来的时间
    --retries=N (default 3) 重试次数
    命令的返回码
    0 成功
    1 失败
    2 不要使用这个码,容器自己定义的
    HEALTCHECK --interval=5m --timeout=3s \ CMD curl -f http://localhost || exit 1
    docker stas 查看各个容器的资源
    docker top web 查看web容器内,进程的占用情况
    如果Dockerfile没有定义,HEALTHCHECK可以
    docker container run 时
    --health-cmd
    --health-interval
    --health-retries
    --health-start-period
    --health-timeout
    

    SHELL

    定义运行命令时的shell,默认是linux默认是sh
    windows 默认是cmd
    syntax
    SHELL ["executable","paramers"]
    

    ONBUILD

    写在自己的dockerfile中,在构建镜像时,不运行,在其他人使用自己镜像做基础镜像,构建镜像时运行
    syntax
    ONBUILD <INSTRUCTION>
    INSTRUCTION 为dockerfile指令
    docker image history --help 查看镜像打包的历史
    docker image prune 删除所有未被使用的镜像
    

    相关文章

      网友评论

          本文标题:Dockerfile

          本文链接:https://www.haomeiwen.com/subject/bwwncktx.html