Php read a log content after executing a script - php

I have a php script that creates a shell script which is run after making it from the same php file, the shell script generates a registry file that I need to read after the script is executed, again from the same php. The php reads the file, but I think it does it before the file is filled or created, if I go back at the browser and execute the php again, then there is content at the textarea. I have tried to solve it adding sleep(), exit() functions and some other strategies but no success. Here are some of the things I've tried:
// Creation of the shell script: Corpus alignment target to origin
......
$cmd = "cwb-align-encode -r $REGDIR -D $CORPUSLOCATION$corpusname/$corpusname"._."$lang_tg.align\n\n";
file_put_contents($scriptfile, $cmd, FILE_APPEND | LOCK_EX);
// Run the corpus indexation script
$cmd = "/bin/bash $scriptfile > /dev/null 2>&1 &";
shell_exec($cmd);
Read the registry file from the same php:
// 1st try: no content at the textarea
echo "<textarea id='txtArea'>".htmlspecialchars(file_get_contents( $REGDIR.$corpusname ))."</textarea>";
// 2nd try: no content at the textarea
echo "<textarea id='txtArea'>".sleep(10); htmlspecialchars(file_get_contents( $REGDIR.$corpusname ))."</textarea>";
// 3rd try: no content at the textarea
echo "<textarea id='txtArea'>".exit(); htmlspecialchars(file_get_contents( $REGDIR.$corpusname ))."</textarea>";
// 4th try: no content at the textarea
echo "<textarea id='txtArea'>".if(filesize($REGDIR.$corpusname) != 0) { echo htmlspecialchars(file_get_contents( $REGDIR.$corpusname )); } else { exit(0); sleep(10); htmlspecialchars(file_get_contents( $REGDIR.$corpusname )); }."</textarea>";

The command line you are using created a new thread that performs the task. PHP wont wait for it, as you do not refer the strout to php (but to /dev/null)
So, by changing the command, you can make PHP wait and thus get the result you expect.
Now I don't know for sure what the correct command is, but I would start with something like
$cmd = "/bin/bash $scriptfile"
Also have a look here. You want the opposite of what that guy wants. It does however give a bit more information about what the command actually does.

Even though the answer given by #Jeffrey is the right one, I realized that this answer is only good enough if the shell script takes short execution time, otherwise your php webpage can expire or hang up, so I gave another try with another php function: header('Refresh: x'), and that made it work right!
So here's what I get now:
// Run the corpus indexation script
$cmd = "/bin/bash $scriptfile > /dev/null 2>&1 &";
shell_exec($cmd);
<textarea id="txtArea" rows="28"><?php if (filesize($REGDIR.$corpusname) != 0) { echo htmlspecialchars(file_get_contents( $REGDIR.$corpusname )); }
else { header('Refresh: 0.5'); htmlspecialchars(file_get_contents( $REGDIR.$corpusname ));} ?></textarea>
UPDATE
Yet another solution:
do { echo htmlspecialchars(file_get_contents( $REGDIR.$corpusname )); } while (filesize($REGDIR.$corpusname) == 0);

Related

How to execute shell from php script

I want to execute this command from a php script
scrapy crawl example -a siteid=100
i tried this :
<?php
$id = 100;
exec('scrapy crawl example -a siteid= $id' $output, $ret_code);
?>
try this:
<?php
$id = 100;
exec('scrapy crawl example -a siteid=$id 2>&1', $output);
return $output;
?>
You actually need to redirect output in order to get it.
If you don't need the output, and just to execute the command, you only need the first part, like this:
exec('scrapy crawl example -a siteid=' . $id);
because you don't put the parameter inside the ' ', you put it outside, read about text concat in PHP.
Depending on if you need the output of the script there are different approaches.
exec executes a command and return output to the caller.
passthru function should be used in place of exec when the output from the Unix command is binary data which needs to be passed directly back to the browser.
system executes an external program and displays the output, but only the last line.
popen — creates a new process that is unidirectional read/writable
proc_open — creates a new process that supports bi-directional read/writable
For your scrapy script I would use a combination of popen and pclose as I don't think you need the script output.
pclose(popen("scrapy crawl example -a siteid=$id > /dev/null &", 'r'));
From the PHP Manual - shell_exec()
$output = shell_exec('ls -lart');
echo "<pre>$output</pre>";
So in short, there is a native PHP command to do what you want. You can also google for exec() which is a similiar function.
phpseclib - Download from http://phpseclib.sourceforge.net/ and include it in your project.
include('Net/SSH2.php');
$ssh = new Net_SSH2("Your IP Here");
if (!$ssh->login('Your User', 'Your Password')) {
exit('Login Failed');
}
$id = 100;
echo "<pre>";
print_r($ssh->exec('scrapy crawl example -a siteid= $id'));
Hope this helps.

prevent file collision PHP with Matlab

i have php file that run from cmd matlab function -> that function is create .txt file and fill it up with the analysis results. then the php file takes this .txt file and sending the information as a string(lines from .txt) to a database (phpmyadmin).
my problem is that the php start to send the info from the .txt while the matlab is still writing to the file.
i thought to solve it with a global var that matlab and php know him, and use it as a flag that Flag determines when Matlab finished building the necessary file. i thought to use the window registry, but it is very complicated. there is any easier way?
thanks alot,
doron
my php file:
unlink('test.txt');
if(isset($_POST['filepath'])) {
$filename = $_POST['filepath'];
$inputDir = "C:\\xampp\\htdocs\\login";
$outputDir = "C:\\xampp\\htdocs\\login";
// here php open the matlab function from the cmd:
$command = "matlab -sd ".$inputDir." -r phpcreatefile2('".$outputDir."\\".$filename.".txt')";
exec($command);
$fileLoc= "".$outputDir."\\".$filename.".txt" ;
echo $fileLoc ;
echo "The following command was run: ".$command."<br/>";
echo $filename." was created in ".$outputDir."<br/>";
echo " Now the txt file will write in the DB <br/>";
// here i tried to check if the file exists and if it is not empty. but its not working because matlab still writing to the file.
while (1) {
if (file_exists("test.txt") ){
echo "check1";
if (filesize("test.txt")!= 0) {
echo "check2";
$file = file('test.txt');
$sql = "INSERT INTO `ID_5525_Medical_record`(`Data`,`AV_Power`,`Highest_Amp`,`90BW`,`Url_figure`) VALUES ('$file[0]','$file[1]','$file[2]','$file[3]','$file[4]')" ;
if(mysqli_query($connection,$sql))
{
unlink('test.txt');
echo "the txt file is now in the DB <br/>";
}
break;
}
else {
echo "i am going to sleep";
sleep(1);
echo "i am awake";
}
}
}
`
Normally, using COM would be the proper way to implement inter process communication between php and MATLAB (Or maybe some alternative, think all are sufficient for this simple task).
Here it seems you call MATLAB only one, you can fix the behaviour appending -wait to the command. This forces launcher to stay open until matlab closes, blocking your PHP-Script at exec($command);. Big disadvantage is, that you have to start Matlab for every function call and close it afterwards. With com one instance can stay open and do everything.

How to execute a bash file from php on a button click

Hi i m trying to execute a bash file which contains a command to run a script file. I had been trying all possible methods but nothing seem to work. I want to run the file and display the result on the web page.
the bash file contains arguments to execute the script. i tried with
system(./bashfile path);
shell_exec(./file path);
if(isset($_POST['submit'])) {
$output = shell_exec('./Users/file.sh ');
echo "<pre>$output</pre>";
but nothing happens. what other ways i could execute the .sh file, help appriciated
system(),exec(),shell_exec(),... functions might be disabled because of security.
Also on the phpinfo page of shell_exec you can find:
This function can return NULL both when an error occurs or the program produces no output. It is not possible to detect execution failures using this function. exec() should be used when access to the program exit code is required.
try:
$command = './Users/file.sh';
$output = '';
exec ( $command, $output, $return_var );
var_dump($output);
var_dump($return_var);

Run a .bat file in command prompt using PHP

I need to run a .bat file in a command prompt whenever I click a button or hyperlink. The code I've written is:
<?php
if(isset($_POST['submit']))
{
$param_val = 1;
$test='main.bat $par';
// exec('c:\WINDOWS\system32\cmd.exe /c START C:/wamp/www/demo/m.bat');
// exec('cmd /c C:/wamp/www/demo/m.bat');
// exec('C:/WINDOWS/system32/cmd.exe');
// exec('cmd.exe /c C:/wamp/www/demo/main.bat');
exec('$test');
}
else
{
?>
<form action="" method="post">
<input type="submit" name="submit" value="Run">
</form>
<?php
}
?>
my main.bat is:
#echo off
cls
:start
echo.
echo 1.append date and time into log file
echo 2.just ping google.com
set/p choice="select your option?"
if '%choice%'=='1' goto :choice1
if '%choice%'=='2' goto :choice2
echo "%choice%" is not a valid option. Please try again.
echo.
goto start
:choice1
call append.bat
goto end
:choice2
call try.bat
goto end
:end
pause
When I click the run button it has to open the command prompt and run the main.bat file, but whenever I click run it says nothing.
$test='main.bat $par';
exec('$test');
... won't work.
PHP only takes $variables in double quotation marks.
This is bad practice also: $test = "main.bat $par";.
Also windows takes backslashes instead of slashes which need to be escaped through another backslash in double quotes.
Use one of these:
$test = 'cmd /c C:\wamp\www\demo\main.bat ' . $par;
or
$test = "cmd /c C:\\wamp\\www\\demo\\main.bat {$par}";
run:
echo shell_exec($test);
Even more fails:
Remove the pause from the end of your script. PHP does not get arround that automatically.
Looking more at the batch file, I bet you don't even need it. Everything inside the batch file can be put into a PHP file.
As Elias Van Ootegem already mentioned, you would need to pipe in STDIN to enter your option (1, 2) into the batch file.
Since you run the PHP script through a browser, on a web server, the .bat file execution occurs on the web server not the client.
No matter if you run your server on the same computer, your bat may be executed but you can not interact with it.
The solution may be to make a bat that takes arguments instead of being interactive, and bring the interaction back to front the PHP script in order to call the bat execution with the correct args.
I‘ve tried this exec on my pc .
your bat would executed but you can't see the black interface. you could try the bat like #echo off
Echo tmptile > tmp.txt like this ,it could create the a file named tmp.txt which tells you. the bat was executed.
Assuming that you just want to simulate an interactive session, you just need to use proc_open() and related functions:
<?php
$command = escapeshellcmd('main.bat');
$input = '1';
$descriptors = array(
0 => array("pipe", "r"), // stdin
1 => array("pipe", "w"), // stdout
);
$ps = proc_open($command, $descriptors, $pipes);
if(is_resource($ps)){
fwrite($pipes[0], $input);
fclose($pipes[0]);
while(!feof($pipes[1])){
echo fread($pipes[1], 4096);
}
fclose($pipes[1]);
$output = proc_close($ps);
if($output!=0){
trigger_error("Command returned $output", E_USER_ERROR);
}
}else{
trigger_error('Could not execute command', E_USER_ERROR);
}

Calling a bash script from PHP to generate another script

I am writing an application which takes text input from the user to generate a text file. A bash script, which takes the generated text file as input should generate another script as output.
I tried using exec command but I am not sure if it works. I want something like this:
exec('generate.sh input.txt generated.sh');
generate.sh takes two inputs:
input.txt file - has user input from PHP page(text separated by '\n')
generated.sh - name of the generated file(to be generated by 'generate.sh').
How can I execute the bash script from PHP to get the above output?
Thanks in advance.
The whole argument to exec needs to be a string like this:
exec('generate.sh input.txt generated.sh');
$generate = '/path/to/generate.sh';
$input = '/path/to/input.txt';
$generated = '/path/to/generated.sh';
if(file_exists($generate))
{
chmod($generate, 0755);
if(file_exists($input))
{
exec($generate.' '.$input.' '.$generated);
}
else
{
echo "Input file not found: ".$input."<br />";
}
}
else
{
echo "Generate file not found: ".$generate."<br />";
}
Furthermore you can also consider system(), shell_exec(), passthru() or proc_open() to execute external commands.

Categories