Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/276.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
当通过PHP(gearman)worker运行时,如何返回R程序状态?_Php_R_Gearman - Fatal编程技术网

当通过PHP(gearman)worker运行时,如何返回R程序状态?

当通过PHP(gearman)worker运行时,如何返回R程序状态?,php,r,gearman,Php,R,Gearman,我有一个PHP脚本(gearman中的worker),它调用Rscript(带有状态进度条),运行良好,但我不知道程序的状态。我的问题是rscript是否可以将运行状态返回到php脚本 <?php print_r(posix_getpwuid(getmyuid())); print_r(pathinfo($YOUR_PATH)); exec(" RScript ~/dynamic.R 'select field1, field2 from table where 1=1 limit 100

我有一个PHP脚本(gearman中的worker),它调用Rscript(带有状态进度条),运行良好,但我不知道程序的状态。我的问题是rscript是否可以将运行状态返回到php脚本

<?php
print_r(posix_getpwuid(getmyuid()));
print_r(pathinfo($YOUR_PATH));
exec(" RScript ~/dynamic.R 'select field1, field2 from table where 1=1 limit 100' ");
?>

您需要向传递一个变量以获取返回值。从文件中:

string exec ( string $command [, array &$output [, int &$return_var ]] )
return\u var
如果return\u var参数与 输出参数,则将显示已执行命令的返回状态 必须写入此变量

因此,您的代码可能如下所示:

exec(" RScript ~/dynamic.R 'select field1, field2 from table where 1=1 limit 100' ", $output, $return_var);

在上面的示例中,
$return\u var
将具有命令的返回状态。

如果重定向输出,然后从文件读取输出,理论上可以使用
exec()
执行此操作,但如果不先找到其PID,则几乎不可能与进程协调。这就是
proc\u open()
的作用
popen()
可能有用,但我猜进度条是写在
stderr
上的,这就是我在这里为您模拟的

这里有一个小程序,应该是您的工作示例:

<?php

$descriptors = array(
    0 => array("pipe", "r"),
    1 => array("pipe", "w"),
    2 => array("pipe", "w")
);

$process = proc_open( "/usr/bin/env ruby ./rlike.rb 1 10", $descriptors, $pipes, getcwd() );
if( is_resource($process) ){
    echo "ran process\n";
    do{
        $status = proc_get_status($process);
        if(! $status["running"]) break;
        fflush($pipes[2]);
        $progressbar = fread( $pipes[2],1 );
        if( $progressbar == "\r" ) echo "\n";
        else echo "$progressbar";
    }while( $status["running"] );
    fclose($pipes[0]);
    fclose($pipes[2]);
    echo "\nProcess complete. \n";
    print_r( $status );
}else{
   echo "Failed to run process.\n";
}
最后,写出进度条的ruby程序如下所示(看看ruby语法的惊人之处:):


从这个例子中,你应该可以得到任何你喜欢的工作。警告:我每次都会重写整个进度条,并使用
\r
返回到行的开头-但根据Rscript进度条的工作方式,情况可能并非如此

你能显示执行Rscript的代码行吗?我已经添加了php代码,我已经使用Djust确认我可以从r通过进度条吗?我不这么认为,实际上。当程序运行时,进度条可能会写出几行输出;
exec()
函数将等待程序完成后返回。因此,当exec返回时,您只需要有一个完整的状态栏。@Savi我认为在exec实际返回之前,您无法获得输出,这将在程序完成时发生。
ran process

|>                    |  00%
|==>                  |  10%
|====>                |  20%
|======>              |  30%
|========>            |  40%
|==========>          |  50%
|============>        |  60%
|==============>      |  70%
|================>    |  80%
|==================>  |  90%
|====================>| 100%
Process complete.
Array
(
    [command] => /usr/bin/env ruby ./rlike.rb 1 10
    [pid] => 60306
    [running] =>
    [signaled] =>
    [stopped] =>
    [exitcode] => 0
    [termsig] => 0
    [stopsig] => 0
)
wait = ARGV[1].to_f || 10.0
repeat = ARGV[2].to_i
repeat = 10 if !repeat or repeat == 0
wait = 1 if !wait or wait == 0
barlen = 20
(repeat+1).times do |t|
    curlen = ( repeat == 0 ? 0 : ( t*barlen/repeat ) )
    bar = ( "%#{curlen}s>" % "" ).gsub( " ", "=")
    $stderr.print sprintf("\r|%- #{barlen+1}s| %3.2d%% ", bar, 100*t/repeat )
    $stderr.flush
    sleep 1 unless t == repeat
end