How to launch unoconv from php file - php

I want to launch the command "unoconv" from a script php.
$command = '/usr/bin/unoconv --server localhost --port 2002 --format=pdf file.rtf >/dev/null 2>/dev/null';
$rc = system( $command );
echo $rc;
The command return no result and the file is not created.
I think is a problem from access with www-data and unoconv.
When I'm launching the command in shell, the file is created.
Any idea?

You can add command unoconv to sudoers.
I do this in this way:
I create wrapper bash script in for example /usr/local/bin where I have command unoconv.
#!/bin/bash
if [ -z "$1" ]; then
echo "Must pass file";
exit 10;
fi
/usr/bin/unoconv -f pdf $1.rtf
after this I adding entry in /etc/sudoers.d:
www-data ALL=NOPASSWD: /usr/local/bin/unoconv.sh
And now you can call script in php:
exec('sudo /usr/local/bin/unoconv.sh '.$fileName);

Try to run
$output = `/usr/bin/unoconv --server localhost --port 2002 --format=pdf file.rtf`;
instead and see error messages.

For me works like this:
$cmd = "/usr/bin/unoconv -f docx files/thefile";
shell_exec($cmd);
of course you have to do this previously (if you lounch your php script from the web):
chown -R www-data:www-data files/

I have found a solution to this problem when running Apache. You have to create the home folder for the www-data user
sudo mkdir /home/www-data
sudo chown www-data /home/www-data
Lastly we will have to edit the home directory and default shell for the www-data user
sudo vim /etc/passwd
For the entry of www-data the last two strings have to be replaced respectively with
/home/www-data
/bin/bash

Simple as this
$output = shell_exec('/opt/libreoffice5.0/program/python unoconv -f rtf test.html');
Edit the path to suite your configuration.
It just works!

You may be running into an issue with LibreOffice, OpenOffice or soffice not being able to write to the current user's $HOME directory.
By running the command below I was able to identify the correct $HOME directory and see the error that was being generated.
$cmd = 'echo $HOME & unoconv -vvvv --format %s --output %s %s 2>/tmp/unoconv.debug.txt';
exec($cmd);
The verbose output of $cmd will be generated written to the file: /tmp/unoconv.debug.txt.
In my case the output was:
Verbosity set to level 5
DEBUG: Connection type: socket,host=127.0.0.1,port=2002,tcpNoDelay=1;urp;StarOffice.ComponentContext
DEBUG: Existing listener not found.
DEBUG: Launching our own listener using /usr/lib64/libreoffice/program/soffice.bin.
Failed to connect to /usr/lib64/libreoffice/program/soffice.bin (pid=32012) in 6 seconds.
Connector : couldn't connect to socket (Success)
Error: Unable to connect or start own listener. Aborting.
The command ran seemed to fine as root, and as sudo -u nobody. On seeing this output I realized there was an issue with the home directory.
Kudos to Dag Wieers for his help - I'm hoping this helps other unoconv devs with their debugging.

Related

shell_exec() not executing shell script

I've a shell_test.php file in /var/www/html folder with this code:
<?php
shell_exec('/var/www/html/config.sh');
?>
config.sh in the same folder has this code:
#!/bin/sh
sudo -u root kill -SIGHUP $(cat /var/www/html/mosquitto/mosquitto.pid)
When I run ./config.sh from folder, it runs.
When I run command in config.sh file directly in terminal, it
works too.
I've added this into sudoers file so that there is no need of password:
www-data ALL=(ALL) NOPASSWD: /var/www/html/config.sh
The thing is it's working fine when run using terminal in both the mentioned ways. Why is not executing when run in PHP?
Your problem is probably, that it is apache, www-data or some other user that is running your script and you try to run it as root.
Try without sudo -u root and change the group of the file to www-data with:
chown root:www-data your-script
As you say "It isn't outputting anything but my mosquitto broker is resetting every time it runs which lets me know"
I think you should replace
shell_exec('/var/www/html/config.sh');
with
$output = shell_exec('/var/www/html/config.sh');
echo $output;
According to php docs "shell_exec — Execute command via shell and return the complete output as a string"
shell_exec doesn't print by default; you have to store the string output and then use it
I made few changes in codes and it worked.
In shell_test.php, I changed code like this:
<?php
shell_exec('sudo -S ./config.sh');
?>
In config.sh, I changed like this:
#!/bin/sh
sudo kill -SIGHUP $(cat /var/www/html/mosquitto/mosquitto.pid)

Run sh file from php with cron

I have an sh file with file-removing commands.
I run it from php like this:
shell_exec("sudo -n ./truncatefiles.sh 2>&1");
Thats works fine if I open the PHP file from browser, but doesnt work from scheduled cron tab.
PHP user: www-data
If i run whoiami from cron, returns same: www-data
I added this to my visudo:
www-data ALL=(ALL) NOPASSWD: /www/sites/..../importscript/truncatefiles.sh
Shell exec for this sh file returns (from cron):
sudo: sorry, a password is required to run sudo
Why works it dirrefent way in cron?
What should I do for get it work?
PLease try to do the following,
Try to log your output from crotab to a file,
* * myscript.php >> /var/log/myjob.log 2>&1
This way you can debug your script.
1. Also the check the user and permissions for your shell script, php file.
2. try with sudo crotab -e

How to access root packages through php?

Issue: Initially, Through command line as a root user,I accessed a package called pandoc (/root/.cabal/bin/pandoc) which was installed in root folder. When I try to access that package through php using shell_exec(),it fails.
Question: Is there any limitation for php shell_exec() not to access root packages for security purposes? If so,how to resolve it?
I tried: Gave write permission to root folder then I could access root packages through
command line not as a root user. yet I couldn't to access it through php shell_exec().
php code:
shell_exec("cd /home/quotequadsco/public_html/pandoc_jats ; sudo -u quotequadsco
-S /root/.cabal/bin/pandoc ex.tex --filter /root/.cabal/bin/pandoc-citeproc
-t JATS.lua -o ex.xml");
and also tried,
shell_exec("cd /home/quotequadsco/public_html/pandoc_jats ;/root/.cabal/bin/pandoc
ex.tex --filter /root/.cabal/bin/pandoc-citeproc -t JATS.lua -o ex.xml");
Expectation: I need to execute pandoc root package through shell_exec() in php.
Added the following line in the /etc/sudoer file
#Defaults requiretty //commented this line
usergroup ALL=(ALL) ALL
PHP code,
shell_exec("cd /home/quotequadsco/public_html/pandoc_jats ;echo password | sudo
-S command"); //added a password for sudo command to run as a root user.
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', true);
$return1 = $shell->exeCmd('pandoc (/root/.cabal/bin/pandoc)');
//the return will be a string containing the return of the command
echo $return1;

PHP exec not executing command

I have used php's exec to execute FFmpeg command but its not woking when I open it in browser. But when i run this php file script in terminal it works fine.And my php safe mode is off. please help me to get it solved. my php code is
<?php
$output=exec("ffmpeg -f image2 -i /home/phedra/imgs/image/img%03d.png -r 12 -s 610x489 /home/phedra/imgs/video/out.avi", $out);
echo $out;
echo $output;
?>
try giving full path where the ffmpeg application is located.
e.g.
/usr/bin/ffmpeg
So your function might look like:
$output=exec("/usr/bin/ffmpeg -f image2 -i /home/phedra/imgs/image/img%03d.png -r 12 -s 610x489 /home/phedra/imgs/video/out.avi", $out);
You must check what is the location of "ffmpeg".
I had this problem and it turned out it was Apache's permission on the public directory.
Note: I am running Ubuntu 14 on AWS
After installing FFmpeg I had to change the /var/www/* ownership to www-data.
sudo chown -R www-data:root /var/www
(the www-data is the important part here)
Then I had the following code running, and it works when I access it via URL (Apache)
// test.php
$run = system("/opt/ffmpeg/bin/ffmpeg -i /var/www/html/input.mp4 -vf scale=640:480 /var/www/html/output.mp4 &");
if($run) {
echo "success";
} else {
echo "failed";
}
The /opt/ffmpeg/bin/ffmpeg is where my FFmpeg is running from. Yours might be /usr/bin/ffmpeg or something else. You can locate it by typing locate ffmpeg in the command line and looking through the list it gives you.
The input file was a public .mp4 file and the output.mp4 file was going to the same location.
Run this in your command line: php test.php - works
Run this from your browser: yourwebsite.com/test.php - works
Note that if you are on windows you must use COMMAS. I.E:
$output=exec('"/usr/bin/ffmpeg" -f image2 -i /home/phedra/imgs/image/img%03d.png -r 12 -s 610x489 /home/phedra/imgs/video/out.avi', $out);
Like #Arfeen mentioned in his answer, you should execute the command with the path of ffmpeg, but, the given path in the answer "/usr/bin/ffmpeg" is not always the same.
First locate your ffmpeg by using the command :
which ffmpeg
The result in my case is :
/usr/local/bin/ffmpeg
Then go back to your php code and replace "ffmpeg" in the command by the path of ffmpeg (which is /usr/local/bin/ffmpeg in my case).

unoconv works from terminal using www-data but not from php script also as www-data

I wrote the following function in php
public static function convert($originFilePath, $outputDirPath, $toFormat)
{
$command = 'echo $PATH & UNO_PATH=/usr/lib/libreoffice unoconv --format %s --output %s %s';
$command = sprintf($command, $toFormat, $outputDirPath, $originFilePath);
exec($command, $output, $result_var);
return compact('output', 'result_var', 'outputDirPath', 'originFilePath', 'toFormat');
}
It did not generate any error message, or any pdf file as well.
In terminal, when I run the unoconv directly as www-data, I had no issues.
This is my result after execution:
2013-05-26 03:05:30 Error: Array
(
[output] => Array
(
[0] => /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
)
[result_var] => 1
[outputDirPath] => /var/virtual/storyzer.com/cake-json/ltequotationapp/webroot/outputfiles/Excel/2
[originFilePath] => /var/virtual/storyzer.com/cake-json/ltequotationapp/webroot/outputfiles/Excel/2/dsadas.xlsx
[toFormat] => pdf
)
Please advise.
The issue is that I am using Nginx and PHP-FPM.
In Nginx the PATH is NOT declared by default.
So there are 2 solutions.
1) you declare it in the fastcgi params for Nginx.
See here.
2) you declare it in the script using putenv() just before you run the unoconv code.
like
putenv('PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/opt/node/bin');
I would also like to add that a certain troubleshooting method helped me to realize this problem. See here.
For a possible solutions see here.
Excerpt from post...
This is what I did to make unoconv work through apache / php code running on Cent OS 6.2 (unoconv version 0.6 and LibreOffice 3.4.5.2):
(This is only a workaround - root cause is not known to me)
Change apache user from /sbin/nologin to /bin/bash (This is done in /etc/passwd file)
Add a new user unoconv
Added a new file /etc/sudoers.d/unoconv with the following contents:
apache ALL=(unoconv) NOPASSWD: /usr/bin/unoconv
(note that my unoconv program is in this location /usr/bin/unoconv - you find it using which unoconv)
Using visudo comment out the followin line (by adding a # at the start of the line)
#Defaults requiretty
Restart sshd and httpd services
Run unoconv like this with php exec() function (you would need to change the input file name and output directory):
exec('sudo -u unoconv /usr/bin/unoconv -f pdf -o bankgenerated Teacher_bulk_upload.csv');
Hope this works out for you
I had the same problem and resolved it by adding two sub-folders in
/var/www/
.cache and .config which are required for unoconv
Env Ubuntu 18.04 server Apache,
unoconv 0.7,
platform posix/linux,
python 3.6.9 (default, Dec 8 2021, 21:08:43),
[GCC 8.4.0],
LibreOffice 6.0.7.3
user#ip-*-*-*-*:/var/www$ sudo mkdir .cache
user#ip-*-*-*-*:/var/www$ sudo chown -R www-data:www-data .cache/
user#ip-*-*-*-*:/var/www$ sudo chmod -R 744 .cache/
user#ip-*-*-*-*:/var/www$ sudo mkdir .config
user#ip-*-*-*-*:/var/www$ sudo chown -R www-data:www-data .config/
user#ip-*-*-*-*:/var/www$ sudo chmod -R 744 .config/
The home folder of www-data is /var/www/ which by default is set to the root user and unoconv can't create the required folders for cache and config.
To check your www-data $HOME
sudo cat /etc/passwd | grep www-data
www-data:x:33:33:www-data:/var/www:/usr/sbin/nologin
I think that is not safe to change the permissions of /var/www/ (to www-data user and group) but is ok to add the .cache and .config folder with www-data permissions. Lets some experts confirm.
P.S. the generator return an error about the docx version but the pdf is generated
$command = 'unoconv -f pdf ' . $path.$file;
exec($command, $output);

Categories