PHP使用proc_open函数并捕获'echo'命令的标准输出

3
我一直在寻找答案,但没有找到直接回答这个问题的方法。首先,我想说的是,我试图实现的目标并不一定特别有用,但部分目的是为了理解PHP如何与其他进程和流进行交互等。
在shell终端上,您可以运行像echo $USER这样的命令,它将输出名为USER的环境变量中的任何内容。
我想知道是否可能执行此命令,然后使用PHP的proc_open函数捕获来自shell echo命令的输出。
这是我目前正在尝试的:
$descriptors = [['pipe', 'r'], ['pipe', 'w'], ['pipe', 'w']];
$handle = proc_open('echo Hello world, $USER!', $descriptors, $pipes, null, ['USER' => 'guest']);
$world = stream_get_contents($pipes[0]);

$world是空的(即'')。

我有几个关于为什么它不起作用的理论[每个理论后面都跟着一个原因,说明为什么每个理论可能是错误的],但我想知道是否有人可以证实其中一个或者提供另一个解释为什么它不能正常工作?


理论1 echo命令在PHP有机会读取输出之前立即终止。[真的吗?没有办法使用proc_open捕获立即终止的命令的输出吗?也许proc_open不是用来做这个的?]

理论2 echo被视为shell内置命令而不是独立可执行文件,这就是它行为不同的原因?[Linux提供了一个名为/bin/echo的可执行文件,难道不能使用那个吗?此外,将echo更改为/bin/echo也无法解决问题]


非常感谢。

1个回答

5

您正在读取$pipes [0]。这是stdin。您想从映射到stdout$pipes [1]读取(并具有写入w标志):

$descriptors = [['pipe', 'r'], ['pipe', 'w'], ['pipe', 'w']];
$handle = proc_open('echo Hello world, $USER!', $descriptors, $pipes, null, ['USER' => 'guest']);
$world = stream_get_contents($pipes[1]);
var_dump($world);

输出

string(20) "Hello world, guest!
"

谢谢指出这个问题! 真不敢相信问题就是这么简单。实际上,这只是原始代码的简化版本,但知道这个确实有效,让我意识到我的原始问题只是因为我没有等待足够长的时间来读取stdout的输出,因为我还启用了非阻塞模式。我会接受这个答案,也许这对于任何刚开始学习如何使用进程IO和流的人来说都是一个有用的参考。 - ec2011

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接