Problems with a PHP shell script: "Could not open input file" - php

Ok, I am trying to create an email logger, that uses a PHP shell script. I have set up CPanel to pipe emails to my script. I am sure this is all configured properly. However I am having problems with the script, well any script for that matter when running it from the shell.
here is an example.
#!/usr/local/bin/php –q
<?php
/* Read the message from STDIN */
$fd = fopen("php://stdin", "r");
$email = ""; // This will be the variable holding the data.
while (!feof($fd)) {
$email .= fread($fd, 1024);
}
fclose($fd);
/* Saves the data into a file */
$fdw = fopen("mail.txt", "w+");
fwrite($fdw, $email);
fclose($fdw);
/* Script End */
?>
Real simple, right? Read from STDIN and write to a file...I thought something was wrong, not able to read STDIN for some reason. Hosting provider allows it, allow_url_open and allow_url_include are both on.
When executing the script via SSH I get the following error:
Could not open input file: âq
So once again I thought that was the script telling me, that is could not read from STDIN
So I tried just a simple script.
#!/usr/local/bin/php –q
<?php
echo 'Hello World';
?>
Same thing:
Could not open input file: âq
So it appears that the PHP program is telling me it is unable to open the script? The script is located in $HOME/mail/forward (CHMOD 755) and the script itself is CHMOD 755, as well the file mail.txt is CHMOD 755
I am really stumped on this.

I just experienced this issue and it was because I was trying to run a script from the wrong directory.. doh! It happens to the best of us.

Have you tried:
#!/usr/local/bin/php
I.e. without the -q part? That's what the error message "Could not open input file: -q" means. The first argument to php if it doesn't look like an option is the name of the PHP file to execute, and -q is CGI only.
EDIT: A couple of (non-related) tips:
You don't need to terminate the last block of PHP with ?>. In fact, it is often better not to.
When executed on the command line, PHP defines the global constant STDIN to fopen("php://stdin", "r"). You can use that instead of opening "php://stdin" a second time: $fd = STDIN;

I landed up on this page when searching for a solution for “Could not open input file” error. Here's my 2 cents for this error.
I faced this same error while because I was using parameters in my php file path like this:
/usr/bin/php -q /home/**/public_html/cron/job.php?id=1234
But I found out that this is not the proper way to do it. The proper way of sending parameters is like this:
/usr/bin/php -q /home/**/public_html/cron/job.php id=1234
Just replace the "?" with a space " ".

Windows Character Encoding Issue
I was having the same issue. I was editing files in PDT Eclipse on Windows and WinSCPing them over. I just copied and pasted the contents into a nano window, saved, and now they worked. Definitely some Windows character encoding issue, and not a matter of Shebangs or interpreter flags.

When you use php CLI argument -q doesn't exist.
I had the same problem when I wrote script in the Windows (eclipse) and I tried run them on Linux. Every line in file from Windows is ended by \r\n. I had to delete \r in first line that contained parser path:
When \r was deleted from first line (mcedit shown \r as ^M) script ran correctly.

Due to windows encoding issue for me
I experienced this "Could not open input file" error. Then I obtained the file using wget from another linux system, and the error did not occur.
The error ws only occurring for me when the file transited through windows.

I know its stupid but in my case i was outside of my project folder i didn't have spark file.

For me the problem was I had to use /usr/bin/php-cgi command instead of just /usr/bin/php
php-cgi is the command run when accessed thru web browser.
php is the CLI command line command.
Not sure why php cli is not working, but running with php-cgi instead fixed the problem for me.

The actual root cause is that the hyphen before "q" on the first line is actually not a standard ASCII hyphen(U+002D), but an en-dash(U+2013). The "a" with the funny hat that PHP reported was the first clue, and then if you look closely the "dash" is too big. This is the kind of thing word processors do to code.

Related

php: use exec command without output to CLI

I am migrating a set of php scripts from Window 2003 / PHP 5.2 to Windows 2012 R2 / PHP 5.6.7
In the scripts exec commands are used, for example to copy files. Commands could look like this:
exec ('copy "C:\ftp\suppliername\upload\*.*" c:\somefolder\ >> output.log');
You could argue that there are better ways to copy files, but I rather wouldn't like to rebuild these scripts right now.
The problem I have is that when there are no files to copy, the error "The system cannot find the file specified." is now shown, while this wan't the case on the old server.
If you just execute the copy command on the command line, the output looks like this:
The system cannot find the file specified.
0 file(s) copied.
This is the same as what gets written to output.log
So apparently the "0 file(s) copied" is getting suppressed somewhere, but not the error.
So my question is, how do I get rid of the error on the commandline? I thought it would be some configuration in php.ini, but after comparing the php.ini from the old and the new server, I couldn't find any essential differences.
I've tried a few things to suppress the error, but with no success:
Adding a # to the exec command
Adding ob_start() and ob_end_clean() before and after the command
Edit: please do not flag as a duplicate. I did see that question before asking my question. the answers given there do not solve my issue. The main question is, why was it working before, you would think that it should still be possible to get it working the same way without modifications to the scripts.
Try adding "2>&1" to your command.
exec ('copy "C:\ftp\suppliername\upload\*.*" c:\somefolder\ >> output.log 2>&1');
This should redirect the error output to output.log
I suppose that this string is being printed to stderr.
You could try to replace your STDERR as described in the post https://stackoverflow.com/a/3823015/146003.
The essential part of the post consists of the lines:
fclose(STDERR);
(...)
$STDERR = fopen('error.log', 'wb');
You can then get rid of error.log. Although I didn't try, you could try to open NIL (see https://stackoverflow.com/a/313115/146003)
First of all, you are redirecting the output of the copy command to a text file, so it will not be ouput to console.
Do this way instead:
exec ('copy "C:\ftp\suppliername\upload\*.*" c:\somefolder\', $output);
var_dump ($output);

popen() in php works from command line but not from browser

I have a simple php script which parses the user input from html form. Since Python does string processing so well, I actually wrote the parser in python. So I forward the user entered string to python script for processing using
$query = "avocados"; // from HTML form
$handle = popen("./NLParser.py $query","r");
$read = fread($handle,2048);
pclose($handle);
when I execute the php from command line interpreter, I get the desired output. But when I visit the same php file from a browser, I get empty string from fread(). I tried checking if the $handle is FALSE and I also read from stderr, no problems there. Please help me figure out this inconsisteny.
I tried running
phpinfo();
The php.ini file used by command line php interpreter was
Loaded Configuration File => /etc/php5/cli/php.ini
and the same entry on web was
Loaded Configuration File /etc/php5/apache2/php.ini
I am using Ubuntu 14.04.1 LTS with PHP Version 5.5.9-1ubuntu4.4. All the files have permission set to 755
Try changing the owner and group of NLParser.py to the ones of your server.

php exec() is not executing the command

I have tried to use exec() with 'whoami' to check if it works and I got the result of
nt authority\system
Now I need to run a .exe file with parameters from php via exec() function.
I tried this in command prompt and it actually runs the program with given parameters. This is the example command.
NOTE the exe file gets 3 inputs (folder, file_name, report_file_nmae)
> ..\..\some_file.exe folder="C:\path_to_folder" param=1.xml report=2.xml
But when I run this command from php file:
exec('..\..\some_file.exe folder="C:\path_to_folder" param=1.xml report=2.xml');
nothing is happening. This is the first time I am using exec() function, so I am not familiar with its details. What is wrong?
I tried using:
\\ instead of \
escapeshellarg() on the directory
added "" around directory folder names
No luck
Addendum:
echo exec($command) // echos < .... why?
or
exec($command, $output);
print_r($output); // Array()
I even changed the permission on the file to full control to all users.
If I call the program from command prompt, I can see the icon appearing next to clock for a second.
But the same call from php will not even call the program.
Edit
Even exec('notepad.exe'); is not working. Something has to be done with php configurations maybe?
I already said that I was new to exec() function. After doing some more digging, I came upon 2>&1 which needs to be added at the end of command in exec().
Thanks #mattosmat for pointing it out in the comments too. I did not try this at once because you said it is a Linux command, I am on Windows.
So, what I have discovered, the command is actually executing in the back-end. That is why I could not see it actually running, which I was expecting to happen.
For all of you, who had similar problem, my advise is to use that command. It will point out all the errors and also tell you info/details about execution.
exec('some_command 2>&1', $output);
print_r($output); // to see the response to your command
Thanks for all the help guys, I appreciate it ;)
You might also try giving the full path to the binary you're trying to run. That solved my problem when trying to use ImageMagick.

Problem with passthru on server

I have a problem trying to run passthru function in my php code (Joomla module). the code is following (this is only a snippet)
ob_start();
passthru("/usr/bin/whois 85.70.231.130 | /usr/bin/grep 'address:'",$code);
$whoisData = ob_get_contents();
ob_end_clean();
$whoisData = str_replace("address:", "", $whoisData);
$whoisArray = split("\n",$whoisData);
echo trim($whoisArray[1]);
when I run this on my localhost, it echoes what it should, but when I run this code on the production server, it echoes nothing and the $code variable contains 127 (command not found). I tryied add absolute paths to these commands into the passthru function, but it didn't helped. Interesting is, that when I run the code right from terminal via ssh and php command, it runs well, but when it's called from application context it doesn't. Does anybody know what I should to do?thanks
SOME EDITS..
safe_mode is on
webserver does not see into /usr/bin and /bin/ folders so what is the best way how to run these commands from php?
usr/bin/grep doesn't look like a valid path to a command.
The missing / at the beginning of the path to the second command might explain the command not found error... even if the first whois command is found.
Have you looked to see if your webserver / php is running chrooted?
print_r(glob('/*'));
if (file_exists('/usr/bin/grep') && file_exists('/usr/bin/whois')) {
print "maybe its a permissions thing?\n";
} else {
print "can't see executables required\n";
}
should give you a clue.
So I have already solved my problem with phpwhois library. I seems like with my server configuration is it unlikely that these functions will be working well. So thanks for your help:)

How do I escape a PHP script to an external editor and return afterwards?

Specifically I have a PHP command-line script that at a certain point requires input from the user. I would like to be able to execute an external editor (such as vi), and wait for the editor to finish execution before resuming the script.
My basic idea was to use a temporary file to do the editing in, and to retrieve the contents of the file afterwards. Something along the lines of:
$filename = '/tmp/script_' . time() . '.tmp';
get_user_input ($filename);
$input = file_get_contents ($filename);
unlink ($filename);
I suspect that this isn't possible from a PHP command-line script, however I'm hoping that there's some sort of shell scripting trick that can be employed to achieve the same effect.
Suggestions for how this can be achieved in other scripting languages are also more than welcome.
You can redirect the editor's output to the terminal:
system("vim > `tty`");
I just tried this and it works fine in windows, so you can probably replicate with vi or whatever app you want on Linux.
The key is that exec() hangs the php process while notepad (in this case) is running.
<?php
exec('notepad c:\test');
echo file_get_contents('c:\test');
?>
$ php -r test.php
Edit: As your attempt shows and bstark pointed out, my notepad test fires up a new window so all is fine, but any editor that runs in console mode fails because it has no terminal to attach to.
That being said, I tried on a Linux box with exec('nano test'); echo file_get_contents('test'); and it doesn't fail as badly as vi, it just runs without displaying anything. I could type some stuff, press "ctrl-X, y" to close and save the file, and then the php script continued and displayed what I had written. Anyway.. I found the proper solution, so new answer coming in.
I don't know if it's at all possible to connect vi to the terminal php is running on, but the quick and easy solution is not to use a screen editor on the same terminal.
You can either use a line editor such as ed (you probably don't want that) or open a new window, like system("xterm -e vi") (replace xterm with the name of your terminal app).
Edited to add: In perl, system("vi") just works, because perl doesn't do the kind of fancy pipelining/buffering php does.
So it seems your idea of writing a file lead us to try crazy things while there is an easy solution :)
<?php
$out = fopen('php://stdout', 'w+');
$in = fopen('php://stdin', 'r+');
fwrite($out, "foo?\n");
$var = fread($in, 1024);
echo strtoupper($var);
The fread() call will hang the php process until it receives something (1024 bytes or end of line I think), producing this :
$ php test.php
foo?
bar <= my input
BAR
system('vi');
http://www.php.net/system

Categories