如何将文件作为参数传递给 php exec?

发布于 2024-12-11 21:02:42 字数 872 浏览 0 评论 0原文

我想知道如何将文件的内容(在我的例子中为 csv)作为参数传递给 php 中的 exec 调用的命令行可执行文件(在 C 或 Objective C 中)。

这是我所做的:用户从这样的 URL 加载其文件的内容:

http://www.myserver.com/model.php?fileName=test.csv

然后以下代码允许 php 解析并加载 csv 文件:

<?php

$f = $_GET['fileName'];
$handle = fopen("$f", "r"); 

$data = array(); 
while (($line = fgetcsv($handle)) !== FALSE) { 
$data[] = $line;
}

?>

我陷入困境的是如何传递此 csv 文件的内容作为 exec 的参数。即使我可以假设 csv 已知只有两列,它有多少行是用户特定的,所以我不能将所有值一一作为参数传递,例如,

exec("/path_to_executable/model -a $data[0][0] -b $data[0][1] .....");

我猜唯一的替代解决方案是写一些东西像这样:

exec("/path_to_executable/model -fileName test.csv");

并让命令行可执行文件进行 csv 解析,但在这种情况下,我认为我需要将 csv 文件物理写入服务器端。我想知道如果几个人同时使用自己不同的 csv 文件访问网页会发生什么,他们是否会互相覆盖?

我想一定有一种非常正确的方法来做到这一点,但我还没有弄清楚。有什么想法吗?谢谢!

I would like to know how I can pass the content of a file (csv in my case) as an argument for a command line executable (in C or Objective C) to be called by exec in php.

Here is what I have done: the user loads the content of its file from an URL like this:

http://www.myserver.com/model.php?fileName=test.csv

Then the following code allows php to parse and load the csv file:

<?php

$f = $_GET['fileName'];
$handle = fopen("$f", "r"); 

$data = array(); 
while (($line = fgetcsv($handle)) !== FALSE) { 
$data[] = $line;
}

?>

where I'm stuck is how to pass the content of this csv file as an argument to exec. Even if I can assume the csv is known to have only two columns, how many rows it has is user-specific, so I cannot pass all the values one by one as parameters, e.g.

exec("/path_to_executable/model -a $data[0][0] -b $data[0][1] .....");

The only alternative solution I guess would be to write something like that:

exec("/path_to_executable/model -fileName test.csv");

and have the command line executable do the csv parsing, but in that case, I think I need to have the csv file physically written on the server side. I'm wondering what happens if several people are accessing the webpage at the same time with their own different csv file, are they over-writing each others?

I guess there must be a much proper way to do this and I have not figured it out. Any idea? Thanks!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

笑,眼淚并存 2024-12-18 21:02:42

我建议将这些数据保存在磁盘上,并在命令行实用程序中加载它 - 这样就不会那么混乱了。但如果您不能这样做,只需一次将其传入 1 行(未解析的):

$command = "/path_to_executable/model";
foreach ($fileData as $line) {
  $command .= ' "'.escapeshellarg($line).'"';
}
exec($command);

然后您可以通过循环 argv 将数据提取到您的实用程序中,其中 argv[0 ] 是第一行,argv[1] 是第二行,依此类推。

I would recommend having that data on disk, and loading it within the command line utility - it is much less messing about. But if you can't do that, just pass it in 1 (unparsed) line at a time:

$command = "/path_to_executable/model";
foreach ($fileData as $line) {
  $command .= ' "'.escapeshellarg($line).'"';
}
exec($command);

Then you can just fetch the data into your utility by looping argv, where argv[0] is the first line, argv[1] is the second line, and so on.

笑红尘 2024-12-18 21:02:42

您可以使用 popen() 来获取要写入的进程的句柄。如果您需要双向(读/写)并且可能需要更多功能,请查看 proc_open()

您也可以将数据写入一些随机文件(以避免多个用户互相踢对方的竞赛条件屁股)。由于

<?php
$csv = file_get_contents('http://www.myserver.com/model.php?fileName=test.csv
');
$filename = '/tmp/' . uniqid(sha1($csv)) . '.csv';
file_put_contents($filename, $csv);
exec('/your/thing < '. escapeshellarg($filename));
unlink($filename);

您还负责可执行文件,因此您可能会弄清楚如何获取传递的参数数量(提示:argc)并读取它们(提示:argv)。像这样通过基于行传递它们:

<?php

$csvRow = fgetcsv($fh);
if ($csvRow) {
  $escaped = array_map('escapeshellarg', $csvRow);
  exec('/your/thing '. join(' ', $escaped));
}

you could use popen() to get a handle on the process to write to. If you need to go both ways (read/write) and might requre some more power, have a look a proc_open().

You could also just write your data to some random file (to avoid multiple users kicking each other's race-conditioned butts). Something along the lines of

<?php
$csv = file_get_contents('http://www.myserver.com/model.php?fileName=test.csv
');
$filename = '/tmp/' . uniqid(sha1($csv)) . '.csv';
file_put_contents($filename, $csv);
exec('/your/thing < '. escapeshellarg($filename));
unlink($filename);

And since you're also in charge of the executable, you might figure out how to get the number of arguments passed (hint: argc) and read them in (hint: argv). Passing them through line-based like so:

<?php

$csvRow = fgetcsv($fh);
if ($csvRow) {
  $escaped = array_map('escapeshellarg', $csvRow);
  exec('/your/thing '. join(' ', $escaped));
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文