【问题标题】:How to correctly format a nested bash command in Dockerfile?如何在 Dockerfile 中正确格式化嵌套的 bash 命令?
【发布时间】:2020-02-22 08:49:06
【问题描述】:

更新:该命令不是有效的 JSON。 Docker 在检测到有效的 JSON 数组时将使用 RUN 的“执行形式”,否则如果检测到无效的 JSON 则回退到使用 RUN 的“shell 形式”。

["bash", "-c", "bash -c 'echo SHLVL: \$SHLVL'"] << \$ is illegal JSON!

但是如果我添加一个额外的\,那么 Bash 将不会在 SHLVL 上进行变量扩展。相反,它打印SHLVL: $SHLVL。详情见https://github.com/moby/moby/issues/40140#issuecomment-546638065


嵌套的 bash 实例递增 SHLVL 环境变量 (http://tldp.org/LDP/abs/html/internalvariables.html)。

例如:

$ echo $SHLVL
1
$ bash -c "echo \$SHLVL"
2
$ bash -c "bash -c 'echo \$SHLVL'"
3

我正在尝试在我的 Dockerfile 中执行相同的命令,但我收到了一个错误(在我的 Github 操作中查看此内容https://github.com/dgroomes/docker-shell-example/commit/20ee36e913729b7cbf7f0e46ffebf359af5cf1a9/checks?check_suite_id=282718710#step:6:20)。

Step 3/3 : RUN ["bash", "-c", "bash -c 'echo SHLVL: \$SHLVL'"]
 ---> Running in 2255c65b43c9
/bin/sh: 1: [bash,: not found

是不是Dockerfile+Bash组合的字符转义问题?

【问题讨论】:

  • 我无法使用您在 Debian 10 上发布的代码重现此问题,而且我什至得到了 14 个步骤,而不是您看到的 15 个步骤。特别是对于Step 11/14 : RUN bash -c echo SHLVL: $SHLVL,我得到的是SHLVL: 1,而不是你的错误
  • @thatotherguy 感谢您的试用!我已经减少了我的回购中的例子,我已经减少了我的问题。你能再试一次吗?
  • 我还打开了一个问题github.com/moby/moby/issues/40140。我尝试了很多转义和无解析的组合。
  • 还将这个问题的“SHVLL”部分分离成另一个问题stackoverflow.com/questions/58573830/…

标签: bash docker dockerfile


【解决方案1】:

您的容器没有安装 bash,请改用sh -c 来运行您的命令。尽管如此,大多数看起来容器已经为您的命令运行/bin/sh。这意味着运行echo SHLVL: \$SHLVL 就足够了。

【讨论】:

【解决方案2】:

字符转义是一个“问题”,在这个例子中是不必要的。

试试这个 Dockerfile 看看类似问题的解释:Bash instances are not nesting in Dockerfile `RUN`

FROM debian:10
RUN ["bash", "-exc", "bash -exc 'echo SHLVL: $SHLVL'"]
RUN ["bash", "-exc", ":; bash -exc ':; echo SHLVL: $SHLVL'"]

那么为什么这里不需要转义: 在第一个变体中,外部 bash 执行命令:

bash -exc 'echo SHLVL: $SHLVL'

由于使用了单引号,所以不需要转义。通过 bash 的 x 设置跟踪变量的扩展并检查 Dockerfile 构建输出:

Sending build context to Docker daemon  14.85kB
Step 1/3 : FROM debian:10
 ---> 8e9f8546050d
Step 2/3 : RUN ["bash", "-exc", "bash -exc 'echo SHLVL: $SHLVL'"]
 ---> Running in 07aaddefac26
+ bash -exc 'echo SHLVL: $SHLVL'
SHLVL: 1
+ echo SHLVL: 1
Removing intermediate container 07aaddefac26
 ---> e82b3fc4b569
Step 3/3 : RUN ["bash", "-exc", ":; bash -exc ':; echo SHLVL: $SHLVL'"]
 ---> Running in 1257c43b276d
+ :
+ bash -exc ':; echo SHLVL: $SHLVL'
+ :
+ echo SHLVL: 2
SHLVL: 2
Removing intermediate container 1257c43b276d
 ---> cfa749c16631
Successfully built cfa749c16631
Successfully tagged test:latest

【讨论】:

    猜你喜欢
    • 2014-04-05
    • 2021-03-31
    • 2017-10-12
    • 2018-04-11
    • 2021-12-21
    • 1970-01-01
    • 1970-01-01
    • 2013-10-30
    • 2017-02-02
    相关资源
    最近更新 更多