What does 2>&1 do in this php snippet? - php

Regarding this code
public function invoke($url)
{
exec('wget 2>&1', $output);
print_r($output);
}
What does the 2>&1 do in this command? I found this on SO but the 2>&1 was not explained
wget is a linux command and I'm running it from PHP using exec().
The code above works. I just need to insert the $url in the correct place and understand the 2>&1.
Related Links
GNU Documentation on Wget

You have several output streams.
The 2 most common are STDOUT (standard output) and STDERR (error output).
Normally you only see the STDOUT output. With exec this is also the only stream that it catches.
Now: the command 2>&1 means litteraly that you pass the output that would go to STDERR to the same output as the normal output. In this case to the exec function of PHP (but mostly to your shell).
This is mostly used when you want to daemonize your apps, and sent all the output to /dev/null, but it can also be used for this case (that you can see everything with PHP).

Related

PHP system() works for some commands, but not all

I have a web server being hosted on a Raspberry Pi B+, running Raspbian. I always have a php "shell" that i can use, but it seems that mine might be messed up somehow. It is an html textarea, with the name="phptorun", and the action file just does eval($_POST['phptorun']);
Since I just have my RPi tucked under a table with no display, I use my phone alot to access the command line.
My question:
When i run something like system("ls"); i get output and the contents of the working directory is displayed. I am working on a C "compiler" (it just uses the command line gcc) but when i do system("gcc");
i get no output at all. i know that the command gcc does put out output, because i have done it before on a different computer.
So why is system("gcc"); not working?
And if gcc isnt installed, wouldnt i get output, just an error?
You need to get more information, it's possible that gcc outputs something to the STDERR for example, which you're missing when you use the system function.
Better try to use the exec function:
exec("gcc 2>&1", $output, $return_code);
Explanation:
gcc 2>&1 redirects STDERR output to the STDOUT
STDOUT is captured into the $output variable
command return code is in the variable $return_code

A certain type of perl file is not giving output on execution from the PHP exec function

My OS is Ubuntu, 14.04, I have lampp. I want to execute a perl file from PHP through my browser. I simply use the exec function (in PHP) to do that and it works. I have seen similar questions in stackoverflow but they aren't related to this.
Example Perl File named test.pl:
#!usr/bin/perl
print "This is a perl file";
Example PHP File named test.php:
<?php
$perl=exec('perl test.pl',$out,$r); //Works successfully
print_r($out); //Outputs Array ( [0]=>This is a perl file )
?>
But I need to execute some other perl file.
I can execute that successfully from the command line. Lets assume name of that file is:
test2.pl
When command is given in command line as
perl test2.pl -u argument1 -m argument2 -p testresult
It takes a fraction of second to execute the above command.
I get the output in command line.
But when I execute the same command from PHP as:
<?php
$perl=exec('perl test2.pl -u argument1 -m argument2 -p testresult',$out,$r);
print_r($out); //Outputs Array ( )
?>
My output is
Array
(
)
Now I am not getting the output, however the perl file is executing, but I am unable to get the output in $out . I can assure you that the perl file was executed because it also makes some kind of file after execution.
I don't understand why its not giving me the output.
I have also tried following functions in php already:,
exec
system
shell_exec
None of them is giving me the output, they are working fine for test.pl but not for test2.pl (test.pl and test2.pl are mentioned above).
My objective is to get the output.
edit: Solved. Thanks to hrunting's answer.
Your second Perl script isn't outputting anything to STDOUT. In your first Perl script, the print statement specifies no output destination, so it will default to STDOUT. In the second Perl script, every print statement either goes to a file or goes to STDERR (with the exception of your --help message). As the PHP exec() function only captures output on STDOUT, you get no output in PHP when you run it, even though you see output when you run it manually.
You have a few options. Two are presented below:
Redirect STDERR to STDOUT when calling exec()
`exec('perl test.pl 2>&1', $out, $r);`
Write output messages to STDOUT in your Perl script
If the output is expected, I would change your print STDERR calls to simple print calls.
There are more options in this Stack Overflow answer:
PHP StdErr after Exec()

How to email output from shell_exec()?

With cron jobs, the output of the file being executed is emailed to me. I recently discovered via this answer that it's possible to asynchronously execute a PHP file using the shell_exec() function. Per the above answer, I've been using the following command:
shell_exec('php /file/path.php parameter1 parameter2 > /dev/null 2>/dev/null &');
I think what is of most interest with regards to this question is the stuff at the end:
> /dev/null 2>/dev/null &
Is there any way to change that so that the output is emailed, like with a cron job?
The line
> /dev/null 2>/dev/null &
Essentially sends the output to a null file. If you take that bit off, the output will be sent to the standard out, which should in turn should email you the results assuming you run it with a cron job.
So,
shell_exec('php /file/path.php parameter1 parameter2');
If you're not running it with a cron job, you'll need to build in the email functionality to the script itself.
First off, shell_exec() is not asynchronous. Execution of the PHP code will be suspended until the shell_exec() call has terminated.
This: > /dev/null tells the shell to redirect stdout from the process being executed to /dev/null, which means it disappears. This: 2> /dev/null does the same, but for stderr in stead of stdout.
If you remove these parts of the shell_exec() call, the call will return whatever is written to stdout:
$result = shell_exec('php /file/path.php parameter1 parameter2');
mail('me#email.com', 'Shell output', $result);
There are also other alternatives to shell_exec() that may suit your needs better. For example popen()andproc_open()` allow more fine grained control over input and output.
Also, since you are executing a PHP script, you may be able to simply use include() or require(), depending on how the script is written. Another option would be to read the file and then execute the PHP code using eval().
Use :
| mail -s "Result of cron job" myemail#company.com
At the end of your command. Also, you can pipe stderr and stdout into stdout 2> &1 | mail....
That should do the trick. Maybe because you use shell_exec("... &"), you'll have to wrap the whole php /file/... | mail -s "result" myemail#company.com in a subshell. like:
shell_exec('(php /file/path.php parameter1 parameter2 2> &1 | mail -s "Result of cron job" myemail#company.com) &')
This is a rather ugly way to get the output to send a message and I'd advise in favor of refactoring the outer call of shell_exec to read stderr and stdout, craft a message and send that to yourself. Meanwhile the | mailsolution should do the trick.
Happy mailing !

PHP - shell_exec output in browser is empty

I'm running a simple wget command in shell_exec()
wget_file.php
<?php
$command = "wget http://mydomain.co/media/bigbigbig.wav";
$output = shell_exec($command);
echo $output;
?>
According to http://www.php.net/shell_exec I can possibly expect an output:
"The output from the executed command or NULL if an error occurred or the command produces no output."
If I run wget_file.php from the command line, I'll see a display of the wget results.
However, if I run it from a browser, no result is given. (but the file does indeed download successfully)
I plan to execute the wget_file.php by calling via cUrl, while passing the url + path.
But would be nice to get a response from the shell_exec(), after execution is completed.
Does anyone know if I'm just missing something to get an output (running in the browser)?
If I run wget_file.php from the command line, I'll see a display of the wget results
wget doesn't output the file contents to console by default, so presumably you're talking about the status information.
I'd imagine this is output to STDERR rather than STDOUT, and it's STDOUT that shell_exec obtains for you in your PHP script:
when you run your script from the command line, you're still seeing the output because both streams are shared by the single terminal window; it's just that you're seeing it directly from wget and not from your PHP script;
in the case of passing it through Apache and to a browser to satisfy a web request, this terminal context is disconnected from the result the user sees.
In your shell command you can redirect the former to the latter:
$command = "wget http://mydomain.co/media/bigbigbig.wav 2>&1";
The comments on the documentation for shell_exec touch on this, particularly the — er — very first one!

I need to run a python script from php

I have to design a interface using PHP for a software written in python. Currently this software is used from command line by passing input, mostly the input is a text file. There are series of steps and for every step a python script is called. Every step takes a text file as input and an generates an output text file in the folder decided by the user. I am using system() of php but I can't see the output but when I use the same command from command line it generates the output. Example of command :
python /software/qiime-1.4.0-release/bin/check_id_map.py -m /home/qiime/sample/Fasting_Map.txt -o /home/qiime/sample/mapping_output -v
try this
$script = 'software/qiime-1.4.0-release/bin/check_id_map.py -m /home/qiime/sample/Fasting_Map.txt -o /home/qiime/sample/mapping_output -v';
$a = exec($script);
If you are not on windows, have you tried adding 2>&1 (redirect stderr to stdout) to the end of the command?
$output = system("python /software/qiime-1.4.0-release/bin/check_id_map.py -m /home/qiime/sample/Fasting_Map.txt -o /home/qiime/sample/mapping_output -v 2>&1", $exitcode);
Found from http://www.php.net/manual/en/function.system.php#108713
Also the doc says that it
Returns the last line of the command output on success, and FALSE on
failure.
So if you are trying to get multiple lines, you may need to redirect it to a file and read that in.
instead of system() try surrounding the code in `ticks`...
It has a similar functionality but behaves a little differently in the way it returns the output..

Categories