PHP how to execute a command - php

I'm trying to use LibreOffice for converting a spreadsheet to another format, when I execute the command from the console it works fine but when I do it from PHP using exec() or system() it doesn't work.
It doesn't show any error or anything, it simply silently fails, if I try executing some simple command like "ls" it works just fine.
This is the command I'm using:
<?php
system("libreoffice --headless -convert-to ooxml '/home/www/path_to_app/file.xlsx' -outdir /home/www/path_to_app/");
I already tried changing the apache User and Group on /opt/lampp/etc/httpd.conf to the same logged in user I am.
I'm wondering if the problem is that the www folder is /home instead of inside my user and that causes permissions problems, but so far couldn't make it work.
Any help will be appreciated.

I solved this problem with the command below :
system('
export HOME=/tmp
libreoffice --headless --invisible --norestore --convert-to pdf --outdir /my/folder /my/file/calc.xls');

I solved this problem with the command below :
exec('libreoffice --headless --invisible --norestore --convert-to pdf --outdir /my/folder /my/file/calc.xls');
Just check rights, libreoffice uses user home folder, If you use default settings for Ubuntu then PHP runs oenter code heren www-data rights and it's home is /var/www/, but default this directory is owned by root.enter code here
In PHP - you can see rigths:
exec('whoami', $arr);
print_r($arr);
In console - You can see your HOME and give correct rights:
su wwww-data
echo $HOME
exit;
chown www-data:www-data /var/www -R

Notwithstanding your $PATH, which drew010 alluded to, I wouldn't do it this way.
LibreOffice is a pretty big program, has lots of code you don't know about, it generates and updates files in a directory in your $HOME, and is certainly not something you're going to be able to run more than one copy of at a time.
So instead of having LibreOffice launched by your web server, and subverting Apache's security by running it as a more privileged user than "www-data" or "nobody", you should make a handler.
First off, verify that you can run your libreoffice ... command line from a terminal. To be extra sure that you don't have any X11 dependencies, run unset DISPLAY (for bash) or unsetenv DISPLAY (for tcsh) in your xterm before you test your command line. Does it break? Fix that problem first. Does it work? Great, then proceed with a handler.
Your handler, in its simplest form, can be a script that loops forever, checking for "files to handle" in a spool directory, and if it finds them, converts them using libreoffice and puts the resultant file where it can be found by your web app.
#!/bin/sh
while sleep 10; do
if [ `ls /var/tmp/myspool/ | grep -c '\.xlsx$'` -gt 0 ]; then
ls /var/tmp/myspool/*.xlsx | while read file; do
/usr/local/bin/libreoffice --headless -convert-to ooxml "$file" yadda yadda
if [ $? = 0 ]; then
mv "$file" "/var/tmp/myspool/done/
fi
done
fi
done
If you don't want the overhead of something "polling" (checking the spool directory every 10 seconds), then you could have your PHP script add a line to a log that gets watched by your handler. For example:
<?php
// process form, save file to spool dir
syslog(LOG_NOTICE, "Saved: " . $filename);
?>
Make sure you've configured syslog to store these messages in, say, /var/log/filelog, then your handler can just tail the log.
#!/bin/sh
tail -F /var/log/filelog | while read line; do
filename="`echo \"$line\" | sed 's/.*Saved: //'`"
/usr/local/bin/libreoffice --headless -convert-to ooxml "$file" yadda yadda
# etc ... error handling and mv as in the other script
done
Get the idea?

I also faced same problem before.....
This solution seems worked for me...
function execInBackground($cmd) {
if (substr(php_uname(), 0, 7) == "Windows"){
pclose(popen("start /B ". $cmd, "r"));
}
else {
exec($cmd . " > /dev/null &");
}
}
$mainFile = "YOUR FILE";
$cmd2 = "export HOME=/tmp
libreoffice --headless --invisible --norestore --convert-to pdf " .
"'$mainFile'";
$saved = getenv("LD_LIBRARY_PATH"); // save old value
$newld = "/usr/lib"; // extra paths to add
if ($saved) {
putenv("LD_LIBRARY_PATH=" . $newld);
}
// set new value
//
// command is loaded using
// libs in the new path list
execInBackground($cmd2);
putenv("LD_LIBRARY_PATH=$saved"); // restore old value

Related

PHP Laravel LibreOffice DOC to PDF not converting via browser run

I'm currently uploading a DOC or DOCX file via DropzoneJS and then convert it to PDF in the server using LibreOffice PHP exec. If I typed it manually in the server then it will convert but if I run it via browser then it is not converting. I'm trying to run the soffice without a sudo but the command run via browser is not working. How can I convert it via browser run?
Manual Command in Terminal:
/opt/libreoffice5.2/program/soffice --convert-to pdf
/var/www/html/my_system/public/msword.doc --outdir
/var/www/html/my_system/storage/app/quotations
Command ls -liah results for folders:
my_system, storage, app, quotations = drwxrwxrwx apache apache
My sudo visudo results (pasted lines with no comments in order):
Defaults requiretty
Defaults !visiblepw
Defaults always_set_home
www-data ALL=NOPASSWD:ALL
robert ALL=NOPASSWD:ALL
apache ALL=NOPASSWD:ALL
PHP File:
$command = '/opt/libreoffice5.2/program/soffice --convert-to pdf /var/www/html/my_system/public/msword.doc --outdir /var/www/html/my_system/storage/app/quotations';
if (!$return) {
echo "PDF Created Successfully";
} else {
echo 'PDF not created. Command = ' . $command . '=' . $return;
}
Thanks.
Found the correct answer via https://superuser.com/questions/627266/convert-file-to-pdf-using-libreoffice-under-user-apache-i-e-when-using-php
Quoting Correct Answer:
So, you need to i) give apache's user a home and ii) give it a
directory it has access to to write in. So, create a tmp directory in
the same folder where you store your webpage and then run the
following php code:
<?php
shell_exec('export HOME=/tmp && libreoffice --headless -convert-to pdf --outdir ./tmp /tmp/ayb/document_34.doc');
?>
I just tested and it works perfectly on my machine. Make sure your
./tmp has its permissions set to 777. Also, you may need to restart
apache if you play aroud with it too much. It stopped working for me
after a while when I made changes and I needed to restart it.

PHP Bash Script calling another Bash script

I have a bash script that takes a parameter is called in PHP by shell_exec(script.sh parameter). Basically, my goal is to call a script that is owned by another user that is not apache.
The script.sh script is a file that contains the following (right now there are some error handling commands):
#/bin/bash
whoami>>whoami
echo $1 >> parameter
while read f; do
env>>envoutput
sudo -i -u archivescriptowner /path/to/archivescript.sh -command archive >> output
done < $1
In my /etc/sudoers file , I have the following:
apache ALL=(archivescriptowner) NOPASSWD: /bin/bash -c /path/to/archivescript.sh *
When I run this script as by running su -s /bin/bash apache and pass a parameter, it works.
When I run it via my button in php, archivescript.sh does not execute
The whoami file has apache written to it
The parameter file has the right file written to it
env shows the following
Term=xterm
LD_LIBRARY_PATH=/path/to/library
PATH=/sbin/:usr/sbin:/bin:/usr/bin
PWD=/var/www/html
LANG=C
SHLVL=4
=/bin/env
PWD is outputting right, that is where my script is right now, it will be moved in the future.
The output file when it is ran by the button click is blank.
I am at a loss as to why this is not working. Any insight would be helpful. Please let me know if I need to give any additional information.
I recently published a project that allows PHP to obtain and interact with a real Bash shell. Get it here: https://github.com/merlinthemagic/MTS
After downloading you would simply use the following code:
$shell = \MTS\Factories::getDevices()->getLocalHost()->getShell('bash', true);
$return1 = $shell->exeCmd('/path/to/archivescript.sh');
echo $return1; //return from your script

Execute Bash Script from PHP

I am calling a bash script from PHP, but I have experienced a strange issue that only specific parameter value passed to bash can be successfully executed:
My PHP code is simple:
$result = shell_exec("/scripts/createUser.sh $uname");
Bash script code:
#!/bin/bash
export PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
usrname=$1
echo -e "Username: $1"
deploy="/wordpress.tar.gz"
dest="/data/$usrname"
mkdir -p $dest
cd $dest
tar zxvf $deploy -C $dest >/dev/null 2>&1
ls $dest
However this script can only successfully mkdir, extract the wordpress.tar.gz and list the folder when $uname == 'test', otherwise nothing happen (even cannot mkdir).
I chown the script to www user and grant execution permission, no help. And already tried run these commands via console as root, they run fine:
/scripts/createUser.sh admin
php deploy.php // in this script $uname == 'admin'
How could this happen? Thanks for your idea!
I recently published a project that allows PHP to obtain and interact with a real Bash shell (as root if requested), it solves the limitations of exec() and shell_exec(). Get it here: https://github.com/merlinthemagic/MTS
After downloading you would simply use the following code:
$shell = \MTS\Factories::getDevices()->getLocalHost()->getShell('bash', false);
$return1 = $shell->exeCmd("/scripts/createUser.sh " . $uname);
//the return will be a string containing the return of the command
echo $return1;
But since you are simply triggering a bunch of bash commands, just issue them one by one using this project. That way you can also handle exceptions and see exactly which command returns something unexpected, i.e. permissions issues.
For commands that run for a long time you will have to change the timeout:
//is one hour enough?
$timeout = 3600000;
$return1 = $shell->exeCmd("/scripts/createUser.sh " . $uname, null, $timeout);

php libreoffice shell_exec not working

I am trying to convert .docx file to .html using php shell_exec in CentOS 6.5
My php code:
$command = "libreoffice --headless -convert-to html resume.docx 2>&1";
$result = shell_exec($command);
echo $result;
When I run the index.php at http://localhost/converter/ it gives me:
javaldx: Could not find a Java Runtime Environment! Warning: failed to read path from javaldx /usr/lib64/libreoffice/program/soffice.bin X11 error: Can't open display: Set DISPLAY environment variable, use -display option or check permissions of your X-Server (See "man X" resp. "man xhost" for details)`
while in terminal it is working perfectly:
cd /var/www/html/converter/
libreoffice --healdess -convert-to html resume.docx
here it creates resume.html in my /var/www/html/converter/.
Hi i have the same problem, i want to convert PDF's from DOCS created with PHP, i'm using OpenSuse 12.3 with LibreOffice, tried many things, finally i detect that the error is in folder:
1.- First check that you don't have disabled shell_exec in php.ini, and open_basedir don't restrict your access folders.
2.- Run the command as a simple user in shell (terminal)
export HOME=/tmp && soffice --headless --convert-to pdf --outdir /srv/www/htdocs/ /srv/www/htdocs/Creecimientos/sic/app/webroot/usuarios/2/8_Pagare_CreePersonas.docx
3.- If it works, you only have to put the correct folders in your code, when i run this code in PHP, it show me a blank page, so i check the access_log of apache for any hint:
[Java framework] Error in function createSettingsDocument (elements.cxx).
javaldx failed!
Warning: failed to read path from javaldx
terminate called after throwing an instance of 'com::sun::star::uno::RuntimeException'
Note: my error was in using export HOME=/tmp, i checked that the folder in root system has 777 for tmp, but the problem was that apache don't acces to it, maybe search for a relative folder of the script, but after test many things i only put a folder with permissons for wwwrun HOME=/srv/www/htdocs/folder_with_777
This is my final code, that works..
<?php
function word2pdf()
{
echo "Procesando";
$result = shell_exec('export HOME=/srv/www/htdocs/Creecimientos/sic/ && soffice --headless --convert-to pdf --outdir /srv/www/htdocs/Creecimientos/sic/ /srv/www/htdocs/Creecimientos/sic/app/webroot/usuarios/2/8_Pagare_CreePersonas.docx');
echo $result;
}
word2pdf();
?>
In fact, it prints: convert srv/www/htdocs/Creecimientos/sic/app/webroot/usuarios/2/8_Pagare_CreePersonas.docx -> /srv/www/htdocs/Creecimientos/sic//8_Pagare_CreePersonas.pdf using writer_pdf_Export, after succes.
I made other changes before in desesperate mode, but none of them solved the problem, tried to change owner to soffice wich found it witch $ ls -l $(which libreoffice), tried with 777, etc..
/* This command will work on centos 6 /7 with installation of libreoffice headless package */
First install package on centos as :
yum install libreoffice-headless
/* following code work to extract text format from */
<?php
$result = exec("export HOME=/tmp/ && /usr/bin/libreoffice --headless --convert-to txt:Text --outdir /tmp filePath");
var_dump($result);
?>
Most likely the user that LibreOffice is ran as, does not have a writeable home directory so LibreOffice fails to create it's config directory and then it cannot create it's config files and then fails to load Java, because it cannot write the default config. A bit silly I know.
Try adding this parameter: -env:UserInstallation=file:///tmp/whateverhere
I don't have enough reputation to comment on TD_Nijboer's answer, but the answer to his specific problem appears to be that soffice needs to be able to read & write config information somewhere. The first place it tries to do this is the libreoffice directory in ~/.config ('~' means "the current user's home directory").
In Debian, by default, the www-data user has the home directory /var/www, and does not have write permission there.
If you make sure it has permission to either create ~/.config itself, or libreoffice within an existing ~/.config, I expect it will work.
2 things, 1st the command is soffice --headless,
2nd i have an similar javaldx error and it has to do with permission.
when executing as root it works fine, but php executes as www-data.
if anybody knows a good way to execute libreoffice from php please let me know.
as i'm getting an error code 77 saying:
[Java framework] Error in function createSettingsDocument (elements.cxx).
javaldx failed!
Warning: failed to read path from javaldx

php command line exec() multiple execution and directories?

I am trying to Execute a multiple commands in php using exec() and shell_exec but i am getting a null value back which i shouldn't and nothing is happening (if i copy and paste the strings below in the command line it will work fine and accomplish the job needed) this is the commands i am using:
$command = "cd /../Desktop/FolderName;";
$command .= 'export PATH=$PATH:`pwd`;';
$command .= 'Here i execute a compiler;';
and then i use the escapeshellcmd()
$escaped_command = escapeshellcmd($command);
then
shell_exec($escaped_command);
any ideas what i am doing wrong and i also tried escapeshellarg() instead of escapeshellcmd()?
Solution: the Problem was the permission of the execution compiler for other owners is non and this was the problem.
because when you are using exec() function in php the owner of the file will be www-data so you need to give permission for the www-data either from the ACL of ubuntu or whatever linux based operating system(you can know the owner by doing this exec('whoami')), or by the files you need to execute.
(Sorry my bad English)
On Linux you can add your Commands in a Shell Script.
You can put this in any file:
#!/bin/bash
cd /../Desktop/FolderName
export PATH=$PATH:`pwd`
EXECUTE COMPILER
And save this as fille.sh
Then, add execution permissions:
chmod +x path/to/file.sh
From PHP, you can call this Script executing:
shell_exec('sh path/to/file.sh');
Hope this helps!

Categories