Я выполняю скрипт TCL из PHP с помощью proc_open.
Может ли кто-нибудь руководить мной.
Настоящий код
<?php $app = 'tclsh84'; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w"), 2 => array("file","C:/wamp/www/tcl/bin/g.txt","w") ) ; $process = proc_open($app, $descriptorspec, $pipes); if (is_resource($process)) { for($i=0;$i<4;$i++) { fwrite($pipes[0], 'source c:/wamp/www/tcl/bin/test.tcl'."\n"); $content= fread($pipes[1],8192) print "$content"; } fclose($pipes[0]); fclose($pipes[1]); proc_close($process); } ?>
Я думаю о сочетании
Вы хотите подождать, пока приложение tcl не будет писать что-то в его stdout в течение определенного времени (предполагая, что это означает конец последней команды), а затем отправить следующую команду / строку в свой stdin?
редактировать:
Похоже, вы можете сразу отправить все команды в оболочку tcl, и они обрабатываются один за другим, то есть оболочка считывает следующую строку ввода / команду, когда она выполняется с предыдущей. Я проверил это со сценарием.
incr a 1 after 1000 puts [concat [clock seconds] $a]
а также
<?php $app = 'c:/programme/tcl/bin/tclsh85.exe'; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w"), 2 => array("file","C:/god.txt","w") ) ; $process = proc_open($app, $descriptorspec, $pipes); if (is_resource($process)) { fwrite($pipes[0], "set a 1\n"); for($i=0;$i<4;$i++) { fwrite($pipes[0], "source c:/helloworld.tcl\n"); } // when all scripts are done the shell shall exit fwrite($pipes[0], "exit\n"); fclose($pipes[0]); do { $read=array($pipes[1]); $write=array(); $except=array($pipes[1]); // wait up to 1 second for new output of the tcl process $ready = stream_select($read, $write, $except, 1, 0); if ( $ready && $read /* is not empty */) { // get the partial output $r = fread($pipes[1], 2048); echo $r; } // is the process still running? $status = proc_get_status($process); } while($status['running']); fclose($pipes[1]); proc_close($process); } ?>
за<?php $app = 'c:/programme/tcl/bin/tclsh85.exe'; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w"), 2 => array("file","C:/god.txt","w") ) ; $process = proc_open($app, $descriptorspec, $pipes); if (is_resource($process)) { fwrite($pipes[0], "set a 1\n"); for($i=0;$i<4;$i++) { fwrite($pipes[0], "source c:/helloworld.tcl\n"); } // when all scripts are done the shell shall exit fwrite($pipes[0], "exit\n"); fclose($pipes[0]); do { $read=array($pipes[1]); $write=array(); $except=array($pipes[1]); // wait up to 1 second for new output of the tcl process $ready = stream_select($read, $write, $except, 1, 0); if ( $ready && $read /* is not empty */) { // get the partial output $r = fread($pipes[1], 2048); echo $r; } // is the process still running? $status = proc_get_status($process); } while($status['running']); fclose($pipes[1]); proc_close($process); } ?>
того<?php $app = 'c:/programme/tcl/bin/tclsh85.exe'; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w"), 2 => array("file","C:/god.txt","w") ) ; $process = proc_open($app, $descriptorspec, $pipes); if (is_resource($process)) { fwrite($pipes[0], "set a 1\n"); for($i=0;$i<4;$i++) { fwrite($pipes[0], "source c:/helloworld.tcl\n"); } // when all scripts are done the shell shall exit fwrite($pipes[0], "exit\n"); fclose($pipes[0]); do { $read=array($pipes[1]); $write=array(); $except=array($pipes[1]); // wait up to 1 second for new output of the tcl process $ready = stream_select($read, $write, $except, 1, 0); if ( $ready && $read /* is not empty */) { // get the partial output $r = fread($pipes[1], 2048); echo $r; } // is the process still running? $status = proc_get_status($process); } while($status['running']); fclose($pipes[1]); proc_close($process); } ?>
Вероятно, вы захотите добавить еще некоторую обработку ошибок. Например, если stream_select () возвращает x раз с таймаутом, что-то могло пойти не так.
edit2:
Пусть оболочка печатает то, что вы можете сканировать для каждого скрипта.
<?php // something that's not in the "normal" output of the scripts $id = 'done'. time(); $app = 'c:/programme/tcl/bin/tclsh85.exe'; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w"), 2 => array("file","C:/god.txt","w") ) ; $process = proc_open($app, $descriptorspec, $pipes); if (is_resource($process)) { fwrite($pipes[0], "set a 1\n"); for($i=0;$i<4;$i++) { $output = ''; $continue = true; $cTimeout = 0; echo 'loop ', $i, "\n"; fwrite($pipes[0], "source c:/helloworld.tcl\n"); fwrite($pipes[0], "puts $id\n"); echo "waiting for idle\n"; do { $read=array($pipes[1]); $write=array(); $except=array($pipes[1]); $ready = stream_select($read, $write, $except, 1, 0); if ( $ready && $read ) { $output .= fread($pipes[1], 2048); // if the delimiter id shows up in $output if ( false!==strpos($output, $id) ) { // the script is done $continue = false; } } } while($continue); echo 'loop ', $i, " finished\n"; } proc_close($process); } ?>
за<?php // something that's not in the "normal" output of the scripts $id = 'done'. time(); $app = 'c:/programme/tcl/bin/tclsh85.exe'; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w"), 2 => array("file","C:/god.txt","w") ) ; $process = proc_open($app, $descriptorspec, $pipes); if (is_resource($process)) { fwrite($pipes[0], "set a 1\n"); for($i=0;$i<4;$i++) { $output = ''; $continue = true; $cTimeout = 0; echo 'loop ', $i, "\n"; fwrite($pipes[0], "source c:/helloworld.tcl\n"); fwrite($pipes[0], "puts $id\n"); echo "waiting for idle\n"; do { $read=array($pipes[1]); $write=array(); $except=array($pipes[1]); $ready = stream_select($read, $write, $except, 1, 0); if ( $ready && $read ) { $output .= fread($pipes[1], 2048); // if the delimiter id shows up in $output if ( false!==strpos($output, $id) ) { // the script is done $continue = false; } } } while($continue); echo 'loop ', $i, " finished\n"; } proc_close($process); } ?>
того<?php // something that's not in the "normal" output of the scripts $id = 'done'. time(); $app = 'c:/programme/tcl/bin/tclsh85.exe'; $descriptorspec = array( 0 => array("pipe","r"), 1 => array("pipe","w"), 2 => array("file","C:/god.txt","w") ) ; $process = proc_open($app, $descriptorspec, $pipes); if (is_resource($process)) { fwrite($pipes[0], "set a 1\n"); for($i=0;$i<4;$i++) { $output = ''; $continue = true; $cTimeout = 0; echo 'loop ', $i, "\n"; fwrite($pipes[0], "source c:/helloworld.tcl\n"); fwrite($pipes[0], "puts $id\n"); echo "waiting for idle\n"; do { $read=array($pipes[1]); $write=array(); $except=array($pipes[1]); $ready = stream_select($read, $write, $except, 1, 0); if ( $ready && $read ) { $output .= fread($pipes[1], 2048); // if the delimiter id shows up in $output if ( false!==strpos($output, $id) ) { // the script is done $continue = false; } } } while($continue); echo 'loop ', $i, " finished\n"; } proc_close($process); } ?>
Пытаться:
$content = ''; while(!feof($pipes[1])) { $content .= fread($pipes[1],8192); }
в$content = ''; while(!feof($pipes[1])) { $content .= fread($pipes[1],8192); }
Это ждет?