简体   繁体   中英

How can I return the output from a Python script that needs to be run as root on a PHP page?

I'm messing around on my raspberry pi and I've just gotten started by installing nginx and PHP. I have a DHT11 temperature sensor hooked up to the GPIO on my Pi, and I'm using a version of this Adafruit script to get the values. Only difference is that it has the proper GPIO values. On my Pi (this is all on my internal network, if it matters) I have index.php sitting in the default nginx directory, and this is what it outputs:

<?php

#echo phpinfo();
$cmd = escapeshellcmd('/home/pi/simpleTemp.py');
$out = shell_exec($cmd);
echo $out;

Right now, I get no output, but I'm very sure that's because the script needs to be run as root. I've added execute permissions to the file but I still get nothing. My PHP install works fine. Should I be using shell_exec or is there a better way?

To run it as root, you can make use of sudo .

<pre>
<?php

$cmd = '/home/pi/simpleTemp.py';
$out = shell_exec("sudo -u root " . escapeshellcmd($cmd));

if (is_null($out))
{
    echo "An error occurred."
    return;
}

echo $out;

This will run the script as root under the defaut shell. If you don't have a $PATH set properly, you may need to specify an absolute path to sudo as /usr/bin/sudo on most systems.

As shell_exec() is a bit limited with regard to error handling, we can also just use exec() . In this example, we'll add some more error handling as well:

<pre>
<?php

if (ini_get('safe_mode'))
{
    echo "Safe mode is enabled; cannot execute!";
    return;
}

$cmd = '/home/pi/simpleTemp.py';
$output = array();
$returnCode = -1;

if (!is_executable($cmd))
{
    echo sprintf("Command '%s' is not executable!", $cmd);
    return;
}

exec(sprintf("/usr/bin/sudo -u root %s 2>&1", escapeshellcmd($cmd)), $output, $returnCode);
echo implode("\n", $output);

if ($returnCode != 0)
{
    echo sprintf("An error occurred (code: %d).", $returnCode);
    return;
}

POSIX programs exit with status code 0 when no errors occurred.

Also note the 2>&1 here, which will redirect the output from Standard Error ( 2 ) to Standard Output ( 1 ) so that error output is not lost.

Another problem we might run into is if the $PATH environment variable is not what we expect. Your Python program might also depend on having a sane $PATH . Use the examples below to get and set $PATH :

<?php
/* To get the current $PATH. */
echo sprintf("Current PATH: %s", getenv('PATH'));

/* To set the $PATH. */
putenv('PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin');

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:

//if the script does not require root permissions you can change the
//second argument on getShell() to false. That will return a bash shell
//with permissions from www-data or apache user.

$shell    = \MTS\Factories::getDevices()->getLocalHost()->getShell('bash', true);
$return1  = $shell->exeCmd('/home/pi/simpleTemp.py');

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM