问题描述
RUN rm /usr/bin/wget
我该怎么做?任何帮助表示赞赏
解决方法
首先要强调:在Dockerfile
中,RUN rm /usr/bin/wget
不会物理删除文件。先前层中的文件和目录在物理上将永远留在那里。因此,如果您尝试使用 rm
删除包含敏感信息的文件,这是行不通的。例如,最近,这种疏忽导致 Codecov 出现了一个引人注目的 security breach。
Docker 层攻击:公开分发的 Docker 镜像应该被压缩或多级处理,以便包含敏感信息的中间层被排除在最终构建之外。
结果是,RUN rm /usr/bin/wget
创建了另一个包含“whiteout”文件 /usr/bin/.wh.wget
的层,并且这个新层位于所有先前层的顶部。然后在运行时,只是容器运行时会隐藏文件,您将看不到它。但是,如果您下载图像并检查每一层,您将能够看到并提取 /usr/bin/wget
和 /usr/bin/.wh.wget
文件。所以,是的,稍后执行 rm
根本不会减小图像的大小。 (顺便说一句,RUN
中的每个 Dockerfile
在最后都会创建一个新层。因此,例如,如果您删除同一个 RUN
中的文件,例如 RUN touch /foo && rm /foo
,您将不会在最终图像中留下 /foo
。)
因此,使用 Jib,如果您要“删除”的文件或目录来自基础映像,您可以做的是为其创建一个新的 whiteout 文件。 Jib 有 <extraDirectories>
feature 可以将任意文件复制到图像中。因此,例如,由于 <project root>/src/main/jib
是默认的额外目录,您可以创建一个空的 src/main/jib/usr/bin/.wh.wget
,它将被处理为图像中的 /usr/bin/.wh.wget
。
当然,如果您真的想物理删除来自基础映像的文件,唯一的选择是重建您的基础映像,使其不包含 /usr/bin/wget
。
为了完整起见:如果您要删除的文件或目录不是来自您的基础映像而是来自 Jib,您可以使用 Jib 图层过滤器扩展 (Maven/Gradle)。 (这是应用层过滤,不涉及 whiteout 文件。)但是,通常没有理由删除 Jib 放置的文件。