ToB企服应用市场:ToB评测及商务社交产业平台
标题:
DockerFile
[打印本页]
作者:
天津储鑫盛钢材现货供应商
时间:
2024-9-12 05:08
标题:
DockerFile
一、Dockerfile 概念
Dockerfile 是一个用于定义 Docker 容器镜像的文本文件。它包含了一组指令,告诉 Docker 如何构建镜像,这些指令包括从基础镜像开始,添加应用程序代码、安装依赖项、设置情况变量,以及设置启动命令等。
执行Dockerfile build能够按照预先设定的指令构建好docker镜像举行使用。
构建步骤
● ① 编写 Dockerfile 文件。
● ② 使用 docker build 命令构建镜像。
● ③ 使用 docker run 命令根据天生的镜像运行容器。
基础知识
● ① 每条
保留字指令
都必须为大写字母 且后面要跟随至少一个参数。
● ② 指令按照从上到下的次序依次执行。
● ③ # 表示解释。
● ④ 每条指令都会创建一个新的镜像层并对镜像举行提交。
执行流程
● ① Docker 从基础镜像上运行一个容器。
● ② 执行一条指令并对容器举行修改。
● ③ 执行雷同 docker commit 的操作提交一个新的镜像层。
● ④ Docker 再基于刚才提交的镜像运行一个新的容器。
● ⑤ 依次类推,直到 Dockerfile 文件中的所有指令都执行完成。
Docker 使用 联合文件体系来构建和管理镜像。联合文件体系允很多个文件体系层叠加在一起,从而创建一个单一的、统一的文件体系视图。Docker 中的每个镜像都由多个层组成,而容器则是镜像的可写副本。
Docker采用联合文件体系,在Dockerfile中表现为每执行一个对应的指令就构建出了一个新的镜像,所有指令执行完成后就构建出了目的镜像。
从应用软件的角度来看,Dockerfile、Docker 镜像和 Docker 容器分别代表软件的三个差别的阶段:
○ Dockerfile 是软件的原质料。
○ Docker 镜像是软件的交付品。
○ Docker 容器则可以认为是软件镜像的运行态,即根据镜像运行的容器实例。
Dockerfile 面向开发,Docker 镜像成为交付标准,Docker 容器则涉及摆设和运维,三者缺一不可,协力充当了 Docker 体系的基石。
● Dockerfile 定义了进程需要的统统东西。Dockerfile 涉及的内容包括执行代码大概是文件、情况变量、依赖包、运行时情况、动态链接库、操作体系的发行版、服务进程和内核进程(当应用进程需要和体系服务以及内核进程打交道的时候,还需要思量如何计划 namespace 的权限控制)等等。
● Docker 镜像就是在编写了一个 Dockerfile 文件之后,使用 docker build 命令来产生一个镜像,当运行 Docker 镜像的时候会真正的提供服务。
● Docker 容器是直接提供服务的。
二、Dockerfile的保留字指令
指令分析FROM指定基础镜像,保举使用小镜像,scratch是一个空镜像,常用于多阶段构建。MAINTAINER指定维护着信息,
已逾期
,可以使用 LABEL xxx=yyy 来取代。RUNRUN 指令在当前镜像层顶部的新层执行任何命令,并提交结果,天生新的镜像层。CMD指定启动容器时默认的命令。比方 CMD [“sh”,“c”,“127.0.0.1”]ENTRYPOINT指定镜像的默认入口以及运行命令 。比方 ENTRYPOINT[“sh”,“c”,“127.0.0.1”]EXPOSE声明镜像内服务监听的端口,一样平常而言,此指令只有指导意义,如:SpringBoot 项目的端口是 8080 ,而指定的 EXPOSE 是 8090 ,当然依据 8080 了。ENV指定情况变量,可以在 docker run 的时候使用 -e 改变。ADD复制指定的 src 路径下的内容到容器中的 dest 路径下,src 可以为 url 会自动下载,也可以为 tar 文件,会自动解压。COPY复制本地主机的 src 路径下的内容到镜像中的 dest 路径下,但是不会自动解压等等。LABEL标注镜像的一些分析信息,常常用来指定维护者的信息。VOLUME创建数据卷挂载点,此处仅是指定挂载点不会绑定挂载目次,详细绑定要到run时指定。USER指定运行容器时的用户名或 UID 。WORKDIR设置工作目次,为后续的 RUN、CMD、ENTRYPOINT 指令设置工作目次。ARG指定镜像内使用的参数(如版本号信息等),可以在 docker build 的时候,使用 --build-args 改变。OBBUILD设置当创建的镜像作为其他镜像的基础镜像是,所指定的创建操作指令。STOPSIGNAL容器退出的信号值。HEALTHCHECK康健查抄。SHELL指定使用 shell 时的默认 shell 类型。
FROM
如果是 Java 应用,可以选择 Java 基础镜像或 Tomcat 基础镜像。
如果是 JS 模块化应用,可以选择 nodejs 基础镜像。
每种语言都有本身的服务器或基础情况镜像,如:Python、Golang、Java、PHP 等。
LABEL
一下两种方式都可以指定label
LABEL multi.label1=“value1” multi.label2=“value2” other=“value3”
LABEL multi.label1=“value1”
multi.label2=“value2”
other=“value3”
RUN
天生的提交镜像将用于 Dockerfile 中的下一步,分层运行 RUN 指令并天生提交符合 Docker 的核心概念,就像 Git 管理源代码一样。
多个 RUN 指令并没有上下文的关系,换言之,多个 RUN 指令都是在同一个目次操作的。
格式1: RUN < command > 格式2: RUN [“executable”, “param1”, “param2”]
CMD和ENTRYPOINT:
CMD和ENTRYPOINT都只会执行一次,如果存在多个,只有末了一个生效。
如果同时设置了这两个命令,且CMD仅仅是选项而不是参数,CMD的内容会作为ENTRYPOINT的参数。
如果两个都是完整的命令,那么会执行末了一条。
ARG
ARG 指令定义了一个变量,用户可以在构建的时候使用 --build-arg name=value 转达,docker build 命令会将其转达给构建器。
–build-arg 指定参数会覆盖 Dockerfile 中指定的同名参数。
如果用户指定了未在 Dockerfile 中定义的构建参数 ,则构建会输出告诫 。
ARG 只在构建时期有效,运行时期无效
。
不发起使用构建时变量来转达注入 github 密码、用户凭据等秘密,由于构建时变量的值可以通过 docker history 来观察到。
ARG 变量定义从 Dockerfile 定义的行开始生效。
使用 ENV 指定定义的情况变量始终会覆盖同名的 ARG 指令。
ENV
ENV 和 ARG 很雷同,但是 ENV 在构建期和运行期都有效,而且使用 ENV 指定定义的情况变量始终会覆盖同名的 ARG 指令。
可以使用 docker run -e name=value 修改 ENV 定义的情况变量。
ENV 在构建期就会被解析并长期化,可以通过 docker inspect image 查看。
ADD
ADD 可以将上下文指定的内容添加(复制)到镜像中,如果是压缩包,ADD 会自动解压;如果是远程 URL ,ADD 会自动下载;但是,
ADD 并没有自动下载远程压缩文件并解压的功能
。
src 路径必须在构建的上下文,不能使用 …/…/xxx 这种方式,由于 Docker 构建的第一步是将上下文目次(包括子目次)发送给 Docker 的守护进程。
如果 src 是 URL ,而且 dest 不以 / 末了,那么就会从 URL 下载文件并将其复制为 dest(名称)。
如果 src 是 URL ,而且 dest 以 / 末了,会自动推断出文件的名称(URL 的末了一部分)并保存到 dest(目次)中。
如果 src 是目次,则将复制目次的整个内容,包括文件体系元数据。
USER
USER 指令和 WORKDIR 指令雷同,都是改变情况状态并影响以后的层,WORKDIR 是改变工作目次,USER 则是改变之后层的执行 RUN 、CMD 、以及 ENTRYPOINT 这类命令的身份。
USER 只是帮助我们切换到指定的用户而已,这个用户必须事先创建好的,否则无法切换。
WORKDIR
WORKDIR 指令为 Dockerfile 中跟随它后面的 RUN 、CMD 、ENTRYPOINT、 COPY、ADD 指令设置工作目次。
WORKDIR 指令可在 Dockerfile 中多次使用。 如果提供了相对路径,则它将相对于上一个 WORKDIR 指令的路径
VOLUME
挂载容器指定的文件夹,如果不存在,会自动创建,纵然启动容器的时候没有指定 -v 参数,也会自动举行匿名卷挂载。
-v 和 VOLUME 挂载出去的目次,主机变,容器内里也会发生变化,但是
① docker commit 提交当前容器的所有变化为镜像,就会丢弃。
② VOLUME [ “/demo”,“/app” ] 容器会自动挂载,在之后对这些目次所操作的变化,也会丢弃
③ 挂载仅仅是为了将外边的数据同步到容器内里
用 VOLUME 声明了卷,那么以后对于卷内容的修改会被丢弃,所以,一定要在 volume 声明之前修改内容 。
FROM alpine
RUN mkdir /demo && mkdir /app
RUN echo 111 > /demo/a.txt
RUN echo 222 > /app/b.txt
# 挂载 容器指定的文件夹,如果不存在,会自动创建。
# 指定了 VOLUME 指令后,即使启动容器的时候没有指定 -v 参数,也会自动进行匿名卷挂载。容器内的 /demo 和 /app ,需要在启动容器的时候,需要使用 -v 参数进行挂载。
# VOLUME 挂载出去的东西,容器改变也不会最终在 docker commit 的时候生效。
# -v 和 VOLUME 挂载出去的目录,主机变,容器里面也会发生变化,但是
# ① docker commit 提交当前容器的所有变化为镜像,就会丢弃。
# ② VOLUME [ "/demo","/app" ] 容器会自动挂载,在之后对这些目录所操作的变化,也会丢弃
# ③ 挂载仅仅是为了将外边的数据同步到容器里面
# VOLUME 的最佳实践是写在 CMD 或 ENTRYPOINT 前面
VOLUME [ "/demo","/app" ]
# 下面的 2 个 RUN 指令没有生效,因为 VOLUME 指定的挂载目录是固化配置,当执行到 VOLUME 的时候就已经写入到容器中了,即使后面容器怎么变,也不会改变。
RUN echo 333 > /demo/a.txt
RUN echo 444 > /app/b.txt
CMD ping www.baidu.com
复制代码
三、虚悬镜像和多阶段构建
3 .1 虚悬镜像
虚悬镜像就是堆栈名和标签名都是 < none > 的镜像,俗称 dangling image。
使用 Dockerfile 写一个虚悬镜像:
FROM ubuntu
CMD echo 'action is success'
复制代码
Dockerfile构建后的镜像结果:
3.2 多阶段构建
多阶段构建的目的是让一个镜像变得更小,构建时耗费的资源更少。
示例: 通例package
### 我们如何打包一个 Java 镜像
FROM maven
WORKDIR /app
COPY . .
RUN mvn clean package
COPY /app/target/*.jar /app/app.jar
ENTRYPOINT java -jar app.jar
## 这样的镜像有多大?
## 我们最小做到多大??
复制代码
Docker底层采用的联合文件体系的多层构建提供了很大的操作空间,在构建项目的每一阶段只使用需要用到的资源,删除多余的资源,每一层都做到最小,达到镜像瘦身的目的。
示例: 多阶段package
# 以下所有前提 保证 Dockerfile 和项目在同一个文件夹
# 第一阶段:环境构建
FROM maven:3.8.4-openjdk-8-slim AS builder
WORKDIR /app
# 此时有坑,想想 Maven 的标准目录结构
COPY src ./src/
COPY pom.xml .
RUN mvn clean package -Dmaven.test.skip=true
# 第二阶段,最小运行时环境,只需要 jre;第二阶段并不会有第一阶段哪些没用的层
# jdk springboot-actutor(jdk)
FROM openjdk:8u282-slim
LABEL maintainer="xxxx@qq.com"
# 从上一个阶段复制内容
COPY --from=builder /app/target/*.jar /app.jar
# 修改时区
RUN ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime && echo 'Asia/Shanghai' >/etc/timezone && touch /app.jar
# 环境变量
# docker run -e JAVA_OPTS="-Xmx512m -Xms64m" -e PARAMS="--spring.profiles.active=dev --server.port=8080" xxx
ENV JAVA_OPTS=""
ENV PARAMS=""
# 运行 jar 包
ENTRYPOINT [ "sh", "-c", "java -Djava.security.egd=file:/dev/./urandom $JAVA_OPTS -jar /app.jar $PARAMS" ]
复制代码
可以使用 .dockerignore 文件,排除上下文中无需参与构建的资源。
合理使用多阶段构建。
合理使用构建缓存加快构建,但是偶尔也会有坑,开发的时候发起还是 docker build -t xxx --no-cache --force-rm . 来构建镜像。
咔咔,Dockerfile详细构建可以问gpt,上边的保留字指令和示例可供参考。
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
欢迎光临 ToB企服应用市场:ToB评测及商务社交产业平台 (https://dis.qidao123.com/)
Powered by Discuz! X3.4