首页 > 解决方案 > 通过 docker-py 使用管道

问题描述

https://github.com/docker/docker-py的示例中,它们将命令的结果返回到 docker 映像,如下所示:

>>> client.containers.run("ubuntu:latest", "echo hello world")
'hello world\n'

我想要的是使用管道 - 例如,如果我能这样做会很棒:

>>> client.containers.run("ubuntu:latest", "echo hello world | wc")
'       1       2      12\n'

但是,相反,我得到了这个:

 >>> client.containers.run("ubuntu:latest", "echo hello world | wc")
    b'hello world | wc\n'

在docker中运行两个命令的最简单方法是什么,第二个从第一个管道传输?

标签: pythondockerdockerpy

解决方案


每当您使用诸如 , 等外壳构造$ENV_VAR|,请确保您实际上有一个外壳来解释它们,否则它们将具有其文字值!要了解为什么您的调用缺少 shell,您必须了解 dockerENTRYPOINTCMD.

如果您查看ubuntu:latest的 dockerfile ,您会发现它是

FROM scratch

而且该文件没有设置一个ENTRYPOINT,只有一个CMD。阅读Dockerfile 中的 CMD 和 ENTRYPOINT 有什么区别?有关差异的一些好看的信息。可以说,在您的情况下,图像名称之后的所有内容都替换了cmd.

containers.run()say的文档command可以是 astrlist. 由此,以及观察到的行为,我们可以推断命令字符串将在空格上拆分,以创建 docker exec 的参数列表。

所以,简而言之,答案是因为|它是一个 shell 构造,但你没有执行任何 shell。有几种方法可以将外壳添加到等式中。最明显的是直接运行shell:

>>> client.containers.run("ubuntu:latest", "bash -c 'echo hello world | wc'",)
'      1       2      12\n'

但是您也可以将入口点设置为 shell,这通常在通用容器中完成(但请注意,您仍然必须确保-c提供,并且必须像以前一样引用整个 shell 命令。入口点仅提供可执行文件,没有任何论据)。

>>> client.containers.run("ubuntu:latest", "-c 'echo hello world | wc'", entrypoint="bash")
'      1       2      12\n'

命令行使用标准输入字段分隔符执行相同的操作:

$ docker run --rm -it ubuntu:latest echo hello world \| wc
hello world | wc

如果我们引用整个内容,我们会破坏输入字段分隔符周围的自动拆分:

$ docker run --rm -it ubuntu:latest "echo hello world \| wc"
docker: Error response from daemon: OCI runtime create failed: container_linux.go:345: starting container process caused "exec: \"echo hello world \\\\| wc\": executable file not found in $PATH": unknown.

等效的python是:

>>> client.containers.run("ubuntu:latest",["echo hello world \\|"])
Traceback (most recent call last):
  [... traceback omitted for brevity ...]
docker.errors.APIError: 500 Server Error: Internal Server Error ("OCI runtime create failed: container_linux.go:345: starting container process caused "exec: \"echo hello world \\\\|\": executable file not found in $PATH": unknown")

推荐阅读