首页 > 解决方案 > 如何在 ddev exec 中使用 'cd' 或 '&&' 或 '>' 重定向等 bash 结构?

问题描述

我正在尝试使用容器中的 bash 做一些复杂的事情,ddev exec但似乎无法让它工作。例如,ddev exec cd /var/tmp导致一个很大的错误信息

Failed to execute command [cd /var/tmp]: Failed to run docker-compose [-f /Users/rfay/workspace/d8git/.ddev/docker-compose.yaml exec -T web cd /var/tmp], err='exit status 126', stdout='OCI runtime exec failed: exec failed: container_linux.go:348: starting container process caused "exec: \"cd\": executable file not found in $PATH": unknown

并尝试使用“||” 并且“&&”或带有“>”的shell重定向也不起作用。

标签: ddev

解决方案


编辑 2019-05-14:截至今天的 ddev 版本 v1.8.0,以下答案已过时,因为ddev exec和 exec 挂钩在 bash 上下文中执行。所以ddev exec "ls | grep php"现在可以正常ddev exec "mysql db <somefile.sql"工作了,就像 exec 钩子一样exec: mysql <somefile.sql

ddev exec(和 config.yaml 中的“exec”钩子)都执行实际的命令,而不是在 shell 的上下文中。“cd”不是 Linux 命令,而是内置的 shell。'&&'、'||' 和 '>' 或 '>>' 也是 shell 结构。所以我们必须做一些变通方法来让它们工作。

但是我们可以明确地使用 bash 来让这些事情起作用:

ddev exec bash -c "cd /var/tmp && ls > /tmp/junk.txt"

在 config.yaml 的 post-start 钩子中做同样的事情:

   hooks:
     post-start:
       - exec: bash -c "cd /var/tmp && ls > /tmp/junk.txt"

请注意,环境变量不会在 exec 语句之间持续存在,因为它们位于不同的 shell 中,因此最好在单行中保持上下文。

另请注意,如果您想重定向 stdout/stderr,您可以在容器内(如上)或主机(重定向 ddev exec 输出)重定向,如下所示:

ddev exec bash -c "cd /var/tmp && ls" >/tmp/junk.txt

将来可能ddev exec会在 bash 的上下文中执行命令以使其更加透明。


推荐阅读