gpt4 book ai didi

Dockerfile:我的 EXPOSE 位置是否正确?

转载 作者:行者123 更新时间:2023-12-02 18:22:52 26 4
gpt4 key购买 nike

在处理 opensource Dockerfile 时收到的一个问题让我很困惑。 ,归结为“为什么要更改图层?” - 所以我试图用我自己的调查来回答这个问题。

我很抱歉这个主题没有很好地定义,但本质上它是关于 docker 层与 docker-cache 的关系。

所以我正在寻找一个没有很好记录的领域的优雅解释。

我对原始 Dockerfile 的更改将 ENV 分成不同的层,提前移动 COPY,稍后公开端口。

原文(简体):

FROM ubuntu:latest
EXPOSE 80
ENV HELLO world \
&& DOCKER whale
RUN # Run stuff
COPY source /to/container
CMD # Do stuff

我的改变:
FROM ubuntu:latest
ENV HELLO world
ENV DOCKER whale # <-- Separate ENV into different layers
COPY source /to/container # <-- Less prone to change, move earlier
RUN # Run stuff
EXPOSE 80 # <-- "Bake in" port later
CMD # Do stuff

假定

据我了解,从 docker-cache 的角度来看, 将 ENV 变量分成不同的层是一种很好的做法,因为 -- 如果用户想要覆盖 ENV -- 只有一个 ENV 需要在它自己的层内更改 ,而不是为了一个而改变包含所有 ENV 的整个层。

但是稍后添加端口 EXPOSE - 感觉不错。这是因为我已经使用 Docker 大约 18 个月了,几乎所有 Docker 的文档和指南都在稍后的 Dockerfile 中公开了该端口。

根据我的经验,我也被引导相信这一点(参加 DockerCon2017 并参加了一些“最佳实践”类(class)) 更容易发生更改/覆盖的层应稍后放置在 Dockerfile 中,以更好地优化 docker-cache,因此没有那么多低级层的变化。

问题:

假设分离 ENV 层、提前移动 COPY 以及 ,我的信念是否正确(或愚蠢)?稍后放置 EXPOSE 层 是一种很好的做法,从优化 Docker 缓存的角度来看,是对原始 Dockerfile 层的整体改进吗?

最佳答案

虽然这个问题有一些固执己见的可能答案,但我会尽量保留来自 docker's docs on this 的事实和其他内容。

在 docker 中正确分层基本上有三个目标(大致排序):

  • 正确性:为了正确性,需要组合/排序某些内容(例如 apt 操作应始终以 apt-get update && ... 开头,而 apt-get update 绝不应位于单独的 RUN
  • 最小化层数:更少的层数通常意味着构建和运行时的更好性能。这通常意味着尽可能合并图层
  • 缓存性能:将可缓存层尽可能推高到文件中,注意如果层失效该层之后的所有层也无效

  • 鉴于此,以下是您提出的一些意见:

    分离 ENV层数

    鉴于上述 (2),您应该保留 ENV尽可能合并图层。用户可以覆盖 --env在运行时不影响构建时分层。是,如果 ENV 之一行在源代码中进行了修改,它将使文件的其余部分(3)无效,但通常出于性能原因,这是折衷的。

    搬家 COPY向上

    通常这不是一个好主意,磁盘上的源是最有可能发生变化的事情之一,如果源发生变化, COPY 中的所有层向下层无效

    搬家 EXPOSE
    这真的无所谓。 EXPOSE是一个几乎微不足道的层(除非您链接容器,否则它实际上什么都不做)。由于它是可缓存的,我会将它放在顶部附近,但同样,计算起来很简单,并且不会真正改变。

    概括

    tl;dr 维护者对所有三个更改说不是正确的,因为这会使构建和运行性能变得更糟。

    关于Dockerfile:我的 EXPOSE 位置是否正确?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45291314/

    26 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com