Dockerfile:将 运行 指令输出到变量中
Dockerfile: Output of RUN instruction into a Variable
我正在编写一个 dockerfile 并希望将 "ls" 命令的输出放入一个变量中,如下所示:
$file = ls /tmp/dir
这里"dir"里面只有一个文件
dockerfile 中的以下 运行 指令不起作用
RUN $file = ls /tmp/dir
您不能保存变量供以后在其他 Dockerfile
命令中使用(如果这是您的意图)。这是因为每个 RUN
都发生在一个新的 shell.
中
但是,如果您只想捕获 ls
的输出,您应该能够在一个 RUN
复合命令中完成。例如:
RUN file="$(ls -1 /tmp/dir)" && echo $file
或者只使用 subshell 内联:
RUN echo $(ls -1 /tmp/dir)
希望这有助于您的理解。如果您有实际的错误或问题需要解决,我可以对此进行扩展而不是假设的答案。
一个完整的例子 Dockerfile
证明这一点是:
FROM alpine:3.7
RUN mkdir -p /tmp/dir && touch /tmp/dir/file1 /tmp//dir/file2
RUN file="$(ls -1 /tmp/dir)" && echo $file
RUN echo $(ls -1 /tmp/dir)
构建时,您应该看到第 3 步和第 4 步输出变量(其中包含在第 2 步中创建的 file1
和 file2
的列表):
$ docker build --no-cache -t test .
Sending build context to Docker daemon 2.048kB
Step 1/4 : FROM alpine:3.7
---> 3fd9065eaf02
Step 2/4 : RUN mkdir -p /tmp/dir && touch /tmp/dir/file1 /tmp//dir/file2
---> Running in abb2fe683e82
Removing intermediate container abb2fe683e82
---> 2f6dfca9385c
Step 3/4 : RUN file="$(ls -1 /tmp/dir)" && echo $file
---> Running in 060a285e3d8a
file1 file2
Removing intermediate container 060a285e3d8a
---> 2e4cc2873b8c
Step 4/4 : RUN echo $(ls -1 /tmp/dir)
---> Running in 528fc5d6c721
file1 file2
Removing intermediate container 528fc5d6c721
---> 1be7c54e1f29
Successfully built 1be7c54e1f29
Successfully tagged test:latest
我无法让 Andy(或任何其他)的方法在 Dockerfile 本身中工作,所以我将我的 Dockerfile 入口点设置为 bash 文件,其中包含:
#!/bin/bash
file="$(conda list --explicit)" && echo $file
echo $(conda list --explicit)
请注意,第二种方法不会呈现换行符,因此我找到了第一种方法 - 通过 $file
变量回显 - 优越。
只需突出显示评论中给出的答案,如果您使用的是 Docker 的现代版本(在我的例子中是 v20.10.5)并且日志没有显示预期的输出,那么这可能是正确的答案,例如,当您 运行 RUN ls
.
您应该在 docker build
命令中使用选项 --progress string
:
--progress string Set type of progress output (auto, plain, tty). Use plain to show container output
(default "auto")
例如:
docker build --progress=plain .
在 docker 的最新版本中,docker 附带的经典构建引擎已升级为显示不同信息的 Builtkit。
您应该看到如下输出:
#12 [8/8] RUN ls -alh
#12 sha256:a8cf7b9a7b1f3dc25e3a97700d4cc3d3794862437a5fe2e39683ab229474746c
#12 0.174 total 184K
#12 0.174 drwxr-xr-x 1 root root 4.0K Mar 28 19:37 .
#12 0.174 drwxr-xr-x 1 root root 4.0K Mar 28 19:35 ..
#12 0.174 drwxr-xr-x 374 root root 12.0K Mar 28 19:37 node_modules
#12 0.174 -rw-r--r-- 1 root root 1.1K Mar 28 19:36 package.json
#12 0.174 -rw-r--r-- 1 root root 614 Mar 28 15:48 server.js
#12 0.174 -rw-r--r-- 1 root root 149.5K Mar 28 16:54 yarn.lock
#12 DONE 0.2s
更多详情。
我正在编写一个 dockerfile 并希望将 "ls" 命令的输出放入一个变量中,如下所示:
$file = ls /tmp/dir
这里"dir"里面只有一个文件
dockerfile 中的以下 运行 指令不起作用
RUN $file = ls /tmp/dir
您不能保存变量供以后在其他 Dockerfile
命令中使用(如果这是您的意图)。这是因为每个 RUN
都发生在一个新的 shell.
但是,如果您只想捕获 ls
的输出,您应该能够在一个 RUN
复合命令中完成。例如:
RUN file="$(ls -1 /tmp/dir)" && echo $file
或者只使用 subshell 内联:
RUN echo $(ls -1 /tmp/dir)
希望这有助于您的理解。如果您有实际的错误或问题需要解决,我可以对此进行扩展而不是假设的答案。
一个完整的例子 Dockerfile
证明这一点是:
FROM alpine:3.7
RUN mkdir -p /tmp/dir && touch /tmp/dir/file1 /tmp//dir/file2
RUN file="$(ls -1 /tmp/dir)" && echo $file
RUN echo $(ls -1 /tmp/dir)
构建时,您应该看到第 3 步和第 4 步输出变量(其中包含在第 2 步中创建的 file1
和 file2
的列表):
$ docker build --no-cache -t test .
Sending build context to Docker daemon 2.048kB
Step 1/4 : FROM alpine:3.7
---> 3fd9065eaf02
Step 2/4 : RUN mkdir -p /tmp/dir && touch /tmp/dir/file1 /tmp//dir/file2
---> Running in abb2fe683e82
Removing intermediate container abb2fe683e82
---> 2f6dfca9385c
Step 3/4 : RUN file="$(ls -1 /tmp/dir)" && echo $file
---> Running in 060a285e3d8a
file1 file2
Removing intermediate container 060a285e3d8a
---> 2e4cc2873b8c
Step 4/4 : RUN echo $(ls -1 /tmp/dir)
---> Running in 528fc5d6c721
file1 file2
Removing intermediate container 528fc5d6c721
---> 1be7c54e1f29
Successfully built 1be7c54e1f29
Successfully tagged test:latest
我无法让 Andy(或任何其他)的方法在 Dockerfile 本身中工作,所以我将我的 Dockerfile 入口点设置为 bash 文件,其中包含:
#!/bin/bash
file="$(conda list --explicit)" && echo $file
echo $(conda list --explicit)
请注意,第二种方法不会呈现换行符,因此我找到了第一种方法 - 通过 $file
变量回显 - 优越。
只需突出显示评论中给出的答案,如果您使用的是 Docker 的现代版本(在我的例子中是 v20.10.5)并且日志没有显示预期的输出,那么这可能是正确的答案,例如,当您 运行 RUN ls
.
您应该在 docker build
命令中使用选项 --progress string
:
--progress string Set type of progress output (auto, plain, tty). Use plain to show container output
(default "auto")
例如:
docker build --progress=plain .
在 docker 的最新版本中,docker 附带的经典构建引擎已升级为显示不同信息的 Builtkit。
您应该看到如下输出:
#12 [8/8] RUN ls -alh
#12 sha256:a8cf7b9a7b1f3dc25e3a97700d4cc3d3794862437a5fe2e39683ab229474746c
#12 0.174 total 184K
#12 0.174 drwxr-xr-x 1 root root 4.0K Mar 28 19:37 .
#12 0.174 drwxr-xr-x 1 root root 4.0K Mar 28 19:35 ..
#12 0.174 drwxr-xr-x 374 root root 12.0K Mar 28 19:37 node_modules
#12 0.174 -rw-r--r-- 1 root root 1.1K Mar 28 19:36 package.json
#12 0.174 -rw-r--r-- 1 root root 614 Mar 28 15:48 server.js
#12 0.174 -rw-r--r-- 1 root root 149.5K Mar 28 16:54 yarn.lock
#12 DONE 0.2s