可以使用unix管道将数据传输到命令行php脚本中吗?我试过了
$> data | php script.php
但预期的data
未显示在$argv
中。有没有办法做到这一点?
答案 0 :(得分:31)
PHP可以从标准输入读取,也为它提供了一个很好的快捷方式:STDIN。
有了它,你可以做以下事情:
$data = stream_get_contents(STDIN);
这只会将所有管道数据转储到$ data。
如果要在读取所有数据之前开始处理,或者输入大小太大而无法放入变量,可以使用:
while(!feof(STDIN)){
$line = fgets(STDIN);
}
STDIN只是$ fh = fopen(“php:// stdin”,“r”)的快捷方式; 相同的方法可以应用于读写文件和tcp流。
答案 1 :(得分:21)
据我了解,$argv
将显示该程序的参数,换句话说:
php script.php arg1 arg2 arg3
但是如果将数据传输到PHP中,则必须从标准输入中读取它。我从来没有尝试过这个,但我认为它是这样的:
$fp = readfile("php://stdin");
// read $fp as if it were a file
答案 2 :(得分:16)
如果你的data
就是这样,你也可以使用-F或-R标志(-F读取并执行后面的文件,-R按字面执行)如果你使用这些标志管道输入的字符串将出现在(常规)全局变量$ argn
简单示例:
echo "hello world" | php -R 'echo str_replace("world","stackoverflow", $argn);'
答案 3 :(得分:4)
您可以输入数据,是的。但它不会出现在$argv
中。它会去stdin。您可以通过以下几种方式阅读,包括fopen('php://stdin','r')
有很好的例子in the manual
答案 4 :(得分:4)
这对我有用:
stream_get_contents(fopen("php://stdin", "r"));
答案 5 :(得分:3)
来看这篇文章,希望制作一个行为类似于shell脚本的脚本,为输入的每一行执行另一个命令...例如:
ls -ln | awk '{print $9}'
如果您正在寻找以类似方式运行的PHP脚本,这对我有用:
#!/usr/bin/php
<?php
$input = stream_get_contents(fopen("php://stdin", "r"));
$lines = explode("\n", $input);
foreach($lines as $line) {
$command = "php next_script.php '" . $line . "'";
$output = shell_exec($command);
echo $output;
}
答案 6 :(得分:1)
如果您希望它显示在$argv
中,请尝试以下操作:
echo "Whatever you want" | xargs php script.php
这将转换为命令行参数的标准输入。
答案 7 :(得分:0)
最佳选择是使用-r选项并从标准输入中获取数据。即,我使用它轻松地使用PHP解码JSON。 这样,您不必创建物理脚本文件。
它是这样的:
docker inspect $1|php -r '$a=json_decode(stream_get_contents(STDIN),true);echo str_replace(["Array",":"],["Shares"," --> "],print_r($a[0]["HostConfig"]["Binds"],true));'
这段代码将显示主机和容器之间的共享文件夹。 请用容器名称替换$ 1或将其放入bash别名中,例如 displayshares(){...}
答案 8 :(得分:0)
我需要获取一个CSV文件并将其转换为TSV文件。当然,我可以将文件导入Excel,然后重新导出,但是有趣之处在于,通过转换器传递数据时,我可以留在命令行中并轻松完成工作!
因此,我的脚本(称为csv2tsv
)是
#!/usr/bin/php
<?php
while(!feof(STDIN)){
echo implode("\t", str_getcsv(fgets(STDIN))), PHP_EOL;
}
我chmod +x csv2tsv
。
然后我可以运行它cat data.csv | csv2tsv > data.tsv
,现在我将数据作为TSV了!
好。没有错误检查(数据是实际的CSV文件吗?)等,但是原理很好。
当然,您可以根据需要链接任意数量的命令。
如果您想进一步扩展这个想法,那么在命令中包含其他选项的能力又如何呢?
简单!
#!/usr/bin/php
<?php
$separator = $argv[1] ?? "\t";
while(!feof(STDIN)){
echo implode($separator, str_getcsv(fgets(STDIN))), PHP_EOL;
}
现在,我可以将默认的分隔符从制表符覆盖为其他内容。可能是|
!
cat data.csv | csv2tsv '|' > data.psv
希望这会有所帮助,并让您看到还能做什么!