I'm attempting to get PHP to call a batch file which will take an RTF file and convert it to a PDF using an OpenOffice macro. I've tested the batch file on the command line and it works fine, but I'm not having any luck calling and using the same batch file from PHP.
My machine OS is XP professional SP 3. I'm running IIS 6 and PHP version 5.2.9.
I've granted execute permissions to the internet user on c:\windows\system32\cmd.exe.
I specified the full path to the batch file being executed and the full path to the RTF file to be converted.
The PHP looks like this where $arg is the RTF to be converted:
$arg = "C:\\web_root\\whatever\\tempOutput.rtf";
$command = "c:\\windows\\system32\\cmd.exe /c c:\\web_root\\whatever\\convert.bat $arg";
Then inside a try-catch I call the exec command:
exec("$command 2>&1 && exit", $ret, $err);
I echo the results after the catch:
echo "ret: ";
print_r ($ret);
print "<br>";
echo "err is ";
echo $err;
print "<br>";
echo "DONE!";
And this is what I see:
ret: Array ( )
err is 0
DONE!
The RTF file does not get converted and I'm not seeing the errors. Any ideas on what I can try next? Thanks!!!
I'm going to bet this is about permissions.
In a typical setup, PHP runs as apache - so you'll want to make sure apache has the rights to execute the batch file.
also, check this relevant SO question, and this google search.
Looks like the output array is empty. Is your batch script supposed to have output?
Also, escapeshellcmd and escapeshellarg should be used
Are you using IIS as your webserver? If so, the PHP exec function will not work by default and you should NOT circumvent the security measures that prevent it from running.
Check your event viewer and you should find some errors pertaining to your problem. Run a query through google for: IIS PHP exec. This should give you a large selection of information about the problem.
Basically, the PHP exec function tries to fork a new cmd.exe instance. IIS prohibits this because it could open a security hole in the system.
The best solution that I have come up with is to have your php script either write the command that you want to execute to a flat file or make a database entry. You will then need to write a seperate script that is launched by the windows scheduler to run every 10 minutes or so that will check your flat file or database for commands to run. The new script will then run the commands and then place either the results or an execution confirmation that your web app will be able to access at a later time.
It's a kludge for sure.
Is PHP running in safe-mode? If so, shell commands are escaped with escapeshellcmd. Perhaps this is the problem?
Do you have control of the server running the PHP script?
Related
I have a situation where I need to call a batch file from a php script... however this batch file needs to run as admin in order to work.
My solution was to create a shortcut to the batch file and check the box to run as admin from the shortcut... however I can't get php to call the shortcut.
I have tried:
exec("C:/path/movefiles_admin.lnk")
and
system("cmd /c C:/path/movefiles_admin.lnk");
Neither of which work. Any suggestions?
Try this:
exec("START C:/path/movefiles_admin.lnk");
START Starts a separate Command Prompt window to run a specified program or command.
You can run nonexecutable files through their file association by typing the name of the file as a command
If your PHP has issues executing shortcut to batch file, try executing simple read and write actions to a test.txt file. (To check whether you have PHP running in safe mode).
If it doesnt do these basic actions then you have some configuration issues.
If a program is started with exec function, in order for it to continue running in the background, the output of the program must be redirected to a file or another output stream. Failing to do so will cause PHP to hang until the execution of the program ends.
Please refer this link for your version of PHP: manual
This question already has answers here:
How do you run a .bat file from PHP?
(7 answers)
php How do I start an external program running - Having trouble with system and exec
(3 answers)
Closed 3 years ago.
Before everyone starts butting in with "security risks" "cant be done" stop there and read the ENTIRE post
I have a web server set up from a home laptop which is serving as a games web server im trying to create a GUI so its easier for us to maintain the server and im trying to use batch files to do the actions on the computer
So to put this into perspective I have my index file index.php
<form method="post">
<input type="submit" name="startServer" value="Start Server">
</form>
<?
if(isset($_POST['startServer'])){
exec('batch/startServer.bat');
}
?>
And my startServer.bat will run on the laptop running the server and will do all the actions nesscary to start our game server so there is another directory "Instance" containing an excutable "Server.exe" which the batch file will run
The issue im having is running the web server and testing this it doesnt work if I open the batch file directly it works but it seems the php code doesnt work
For clarification I am using apache and my browser is chrome
And just a quick question for anyone willing to answer the route im going is correct right? Using php would allow everything to run on the machine hosting the server so the end user will only see the GUI and the server would run the batch files and everything on the web server and not the local machine if that makes sense?
EDIT: To be more clear about what's going on the function exec runs but it just hangs like the application is loading I need a solution that will actually open the application are my host computer for example if I wanted to open up notepad I press a button on the Web server and notepad will open on the computer
EDIT 2: I would like to note that I dont exactly need to use the exec function and I have tried all the answers to date 7/19/2017:3:45pm none are working if I do something on the sorts echo exec('start text.bat'); I will get a This is a test to show your batch is working and simply just have echo ..... in the batch file the main issue I am having is the server is not physically showing the opened file like displaying the GUI lets just take notepad for example
I can open notepad and get some return value as long as my batch file closes notepad once its finished running however the GUI for notepad is never displayed and thats very important
I read in a few articles about using apache as a service which im pretty sure I am but I do know that xaammp has suffiecient priveleges and I have checked the box that says "Allow apache to interact with desktop" however no GUI is popping up thats the main point I guess im trying to get across is I need to display the GUI not just open the file as a background service.
If it makes answering easier I am open to switching programming languages if theres one that can do what I want easier
Your theory is correct, it will run on the server however you may have issues running applications directly from php (with this method afaik it does not detach from the PHP, and the webapp "hangs" while the application is running).
Make sure: return values are printed / logged. Just an
<?php
if(isset($_POST['startServer'])){
echo exec('batch/startServer.bat');
}
?>
Could point you to the right direction. The exec function may have been disabled in your distribution.
Using
<?php
instead of
<?
is highly advised, by default short_tags are not enabled in most distributions (wamp, xamp, etc).
Set debug mode and print everything to get information about the problem:
<?php
ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting(E_ALL);
if(isset($_POST['startServer'])){
echo exec('batch/startServer.bat');
}
?>
If you don't have any response, try a simple batch file with a "hello world" to test if it works.
Be aware, the rights and limitations are comes from the php environment, the batch file inherits the same rights running the PHP code / Apache (in case of mod_php)
In php manual about exec function, there is a note :
Note: If a program is started with this function, in order for it to
continue running in the background, the output of the program must be
redirected to a file or another output stream. Failing to do so will
cause PHP to hang until the execution of the program ends.
I think "hangs like the application is loading" is your application waiting for the bat file terminated / closed to get the output result
Let's try another approach, i found it here, the concept is to create a scheduler that execute the program you want and call it using command.
hope this help :
shell_exec('SCHTASKS /F /Create /TN _notepad /TR "notepad.exe" /SC DAILY /RU INTERACTIVE');
shell_exec('SCHTASKS /RUN /TN "_notepad"');
shell_exec('SCHTASKS /DELETE /TN "_notepad" /F');
If this doesn't work
Check whether you have declared safe_mode = Off inside php.ini
From here:
How do you run a .bat file from PHP?
Have you tried:
system("cmd /c C:[path to file]"); ?
You might need to run it via cmd, eg:
system("cmd /c C:[path to file]");
Or Try following options
1.
<?php
exec('c:\WINDOWS\system32\cmd.exe /c START C:\Program Files\VideoLAN\VLC\vlc.bat');
?>
2.
When you use the exec() function, it is as though you have a cmd terminal open and are typing commands straight to it.
Use single quotes like this $str = exec('start /B Path\to\batch.bat');
The /B means the bat will be executed in the background so the rest of the php will continue after running that line, as opposed to $str = exec('start /B /C command', $result); where command is executed and then result is stored for later use.
<?php
pclose(popen("start /B test.bat", "r")); die();
?>
i think this is a containment issue.
if you run the app under the process of php run by iiswebuser when php terminates it will close all spawned child processes in windows. there is a very quick way a command to break an application out of the child process containment using the start command.
if(isset($_POST['startServer'])){
exec('start batch/startServer.bat');
}
Diagram of containment as i explained it (simplisticly)
IIS (IIS runs as an IISUser)
php (application)
cmd.exe (batch)
using start bring it to the root of that tree
IIS (IIS runs as an IISUser)
php (application)
cmd.exe (batch)
Baim Wrong was correct in the first part of the response: you have to redirect output of the script or your PHP code will hang. Also, you have to move process in the background.
This is easy to do on *nix:
system("/usr/local/bin/shell.sh >> /tmp/log.log 2>&1 &");
I know that you can redirect the output on Windows but not sure how to move the process in the background. You should check DOS manual or try with power shell.
you can use either system or exec php function
$path = __DIR__ . '/batch/startServer.bat';
exec('cmd /c start ' . $path);
or
$path = __DIR__ . '/batch/startServer.bat';
$lastLine = system('cmd /c start ' . $path);
You are having some issue about running application directly from exec. I was having the same issue of running file using exec. It was solved by passing another parameter 2>&1.
exec('some_command 2>&1', $output);
print_r($output); // to see the response to your command
Check the values printed by output see exec function
<?php
ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting(E_ALL);
$output = array();
if(isset($_POST['startServer'])){
exec('batch/startServer.bat 2>&1', $output);
print_r($output);
} else {
echo "Not posted";
}
?>
I have a php script which calls a shell script as below -
#!/bin/bash
timestamp=$(date +"%d-%m-%Y %H:%M:%S")
echo $timestamp >> results
The php script -
<?php
$mycmd = exec('/bin/bash exectest.sh',$op,$er);
var_dump($mycmd);
var_dump($op);
echo $er."\n";
?>
The php script returns error code 1 for $er but when i tried to modify the shell script to just print instead of writing to a file. the Php script then returns 0 and succeeds.
Any ideas of where I need to fix this?
I have tried giving the full path for the script and also this is the same case when i tried using a python script in place of a shell script.
Your observation indicates that this is most likely a permission problem, e.g. the user running PHP does not have write permission to either the results file in its current working directory or the directory itself (if the file does not exist yet).
It happened to be running on an AFS machine hence required afs priviledges for httpd.
fs sa . http write
sorted the issue.
I am running a local WAMP on my Windows 7 with a PHP script that executes a windows command as follows:
`exec('"%CD%\files_for_redistribution\ppt2html5.exe" /i:"%CD%\test.ppt" /o:"%CD%\output.html" /title:title /desc:description /author:author /keywords:keywords',$output,$error);`
The command when run from a batch file does the job well but when run from PHP script, gives an error:Presentation opening error: PowerPoint could not open the file.
The intention of the command is to convert PowerPoint to HTML using a third party software called ppt2html5.exe where test.ppt has to be converted to output.html.
I have found lot of blogs discussing about exec function not working properly but nothing really helped me to deal with this error as it runs the command but cannot open the file.
It would be great if somebody could help me with this.
Check if safe mode is on, because that activates escapeshellcmd and some characters are escaped.
Assuming that the string that you are passing to exec(), including percentage signs, routes and parameters are right, your problem may be related to permission of files and user executing apache + php, check that.
Fixed by adding a folder named Desktop inside C:\Windows\System32\config\systemprofile.
Source:http://www.sitepoint.com/forums/showthread.php?956457-Windows-2008-PHP-new-COM%28powerpoint-application%29
I have a PHP website and I would like to execute a very long Python script in background (300 MB memory and 100 seconds). The process communication is done via database: when the Python script finishes its job, it updates a field in database and then the website renders some graphics, based on the results of the Python script.
I can execute "manually" the Python script from bash (any current directory) and it works. I would like to integrate it in PHP and I tried the function shell_exec:
shell_exec("python /full/path/to/my/script") but it's not working (I don't see any output)
Do you have any ideas or suggestions? It worths to mention that the python script is a wrapper over other polyglot tools (Java mixed with C++).
Thanks!
shell_exec returns a string, if you run it alone it won't produce any output, so you can write:
$output = shell_exec(...);
print $output;
First off set_time_limit(0); will make your script run for ever so timeout shouldn't be an issue. Second any *exec call in PHP does NOT use the PATH by default (might depend on configuration), so your script will exit without giving any info on the problem, and it quite often ends up being that it can't find the program, in this case python. So change it to:
shell_exec("/full/path/to/python /full/path/to/my/script");
If your python script is running on it's own without problems, then it's very likely this is the problem. As for the memory, I'm pretty sure PHP won't use the same memory python is using. So if it's using 300MB PHP should stay at default (say 1MB) and just wait for the end of shell_exec.
A proplem could be that your script takes longer than the server waiting time definied for a request (can be set in the php.ini or httpd.conf).
Another issue could be that the servers account does not have the right to execute or access code or files needed for your script to run.
Found this before and helped me solve my background execution problem:
function background_exec($command)
{
if(substr(php_uname(), 0, 7) == 'Windows')
{
pclose(popen('start "background_exec" ' . $command, 'r'));
}
else
{
exec($command . ' > /dev/null &');
}
}
Source:
http://www.warpturn.com/execute-a-background-process-on-windows-and-linux-with-php/
Thanks for your answers, but none of them worked :(. I decided to implement in a dirty way, using busy waiting, instead of triggering an event when a record is inserted.
I wrote a backup process that runs forever and at each iteration checks if there is something new in database. When it finds a record, it executes the script and everything is fine. The idea is that I launch the backup process from the shell.
I found that the issue when I tried this was the simple fact that I did not compile the source on the server I was running it on. By compiling on your local machine and then uploading to your server, it will be corrupted in some way. shell_exec() should work by compiling the source you are trying to run on the same server your are running the script.