Dockerfile中使用exec形式运行echo为什么会创建/etc/resolv.conf?

49次阅读
没有评论

问题描述

在构建Docker镜像时,在Dockerfile中使用了一行指令,内容如下:

RUN ["echo", "'anything'", ">", "./a_file"]

然而这行指令没有生效,用户最终不得不使用以下形式才成功:

RUN ["sh", "-c", "echo 'anything' > ./a_file"]

在修复这个问题之前,用户使用了 dive 工具来查看这个指令在镜像中产生了什么改变。令人惊讶的是,a_file 并没有被创建,反而是一个空的 /etc/resolv.conf 文件被创建了。

解决方案

请注意以下操作可能受到Docker版本差异影响。

为什么会创建 /etc/resolv.conf

创建空的 /etc/resolv.conf 文件是Docker引擎通过绑定挂载在容器中注入的,其中的设置是与Docker引擎本身相关的。父文件系统中的空文件是这种绑定挂载的副作用,你可以安全地忽略它。

修复 a_file 未创建的问题

如果 a_file 没有被创建,需要检查该文件是否在一个卷(volume)中。在使用 RUN 命令中的临时(匿名)容器中创建的卷,对卷的更改不会包含在对容器文件系统的更改中。因此,如果 a_file 没有被创建,可能是因为它位于一个卷中。

为确保 a_file 被创建并包含在容器文件系统中,你可以尝试以下方法:

方法1:使用exec格式的echo指令

如果你希望继续使用exec格式的 echo 指令,可以尝试以下步骤:

  1. 确保 a_file 所在的目录在Dockerfile中是可写的,并且没有被定义为卷。
  2. RUN 指令中,使用正确的语法来执行 echo 指令,如下:
    Dockerfile
    RUN echo 'anything' > ./a_file

方法2:使用shell格式的echo指令

另一种方法是使用shell格式的 echo 指令,这通常更灵活。你可以通过以下步骤来实现:

  1. 确保 a_file 所在的目录在Dockerfile中是可写的,并且没有被定义为卷。
  2. RUN 指令中使用shell格式的 echo 指令,如下:
    Dockerfile
    RUN sh -c "echo 'anything' > ./a_file"

通过上述方法,你应该能够在Docker镜像中成功创建 a_file 文件。

总结

在使用Docker构建镜像过程中,遇到了使用exec格式的 echo 指令不按预期工作的问题。出现的 /etc/resolv.conf 文件是Docker引擎通过绑定挂载注入的一个副作用,不必过于担心。如果 a_file 没有被创建,你可以根据以上方法来进行修复,确保目录权限和文件路径设置正确,以便成功创建文件。

正文完