tera_789
tera_789

Reputation: 529

Python modules are not imported when running python script from PHP

I have a Python script, which works fine when I run it in Terminal. Here it is:

import bs4, requests, json, sys
from sys import argv

def getFsmonData(link):
    res = requests.get(link)
    res.raise_for_status()
    soup = bs4.BeautifulSoup(res.text)

    # Get table data
    tds = soup.select('td')
    new_td_list = []
    for i in range(len(tds)):
        inner_td_list = []
        for y in range(len(tds)):
            inner_td_list.append(tds[y].getText())
        new_td_list.append(inner_td_list)
    print(inner_td_list)
    td_list_json = json.dumps(inner_td_list)
    tdf = open("/path/to/file/data/td_data.txt", "w")
    tdf.write(td_list_json)
    tdf.close()

getFsmonData(sys.argv[1])

But now I am trying to run it from PHP and I get the following error:

Traceback (most recent call last): File "/path/to/file/example.py", line 1, in import bs4, requests, json, sys ModuleNotFoundError: No module named 'bs4'

I guess PHP thinks I do not have this module installed, but I am not sure of course. Here is my PHP code:

<?php
    $link = $_POST['dn-link'];

    if (isset($_POST['submit'])) {
        system('/usr/bin/python3 /path/to/file/example.py ' . escapeshellarg($link) . ' 2>&1', $retval);
    }
?>

Who can help solving this issue?

Upvotes: 0

Views: 3066

Answers (3)

Dan
Dan

Reputation: 41

To best work around this and ensure you do not compromise the PHP profile, setup a virtual environment for you python installation/application ensuring to pip install all required modules.

Now this is done we can call this instance directly to execute the script. You will however need to ensure that home is set in PHP so that it you can use the actual file paths.

<?php
// Set the 'HOME' environment variable (replace with the appropriate path)
putenv('HOME=/home/yourusername');

// Execute the Python script
exec("/home/yourusername/virtualenv/application_name/python/3.9/bin/python /home/yourusername/location_of_script/example.py", $output, $return_var);

// Check the output and return status once verified this can be edited to just be the expected output
echo "Output: " . implode("\n", $output) . "<br>";
echo "Return Status: " . $return_var;
?>

I know this is old but I found it after having the same issue and after a lot of debugging found the answer. This is here for anyone like me who is having the same issue.

Upvotes: 0

Jamie Marshall
Jamie Marshall

Reputation: 2304

I think your misunderstanding the permission issue. It's not that you need to add it PHP. It's that your OS keeps track of permissions, and the permission you have assigned to your PHP interpreter and your Python interpreter are misaligned. There are two permissions that usually people mix up here - USER which is login level access and SYSTEM which is system wide access. If your on your own dev machine then add both to SYSTEM.

We need to know your OS to be able to fully answer, i'm going to guess Mac OS in which case would be this (I think, can't test it right now).

sudo nano "pathOfYourInterpreter"

The other thing could be happening is that the libraries you're tryng to import are somewhere where the current sys path you have setup can't reach them. For example if you have your sys variable for Python set to the directory where the interpretor is but the scripts you're importing are in a different folder. In that case you have several options for accessing those scripts.

  1. Set the current working directory to the folder where they're located before importing with:

    os.chdir("locationOfScript/")
    import script.py
    
  2. Add a sys Path at runtime:

     sys.path.append("locationOfScript/)
    

There are more methods of attack, but I think this should get you started.

Upvotes: 2

Dylan Schroder
Dylan Schroder

Reputation: 41

Most likely, when your PHP script executes your Python script, its executing it as a different user (possibly super user). What you can do is check if the packages are installed under the super user by doing

sudo pip list

or if you're using python3

sudo pip3 list

see if the packages you we're wanting to use are listed from this command.

If they aren't listed, you can easily install them via the command:

sudo pip install <pkg name>

or

sudo pip3 install <pkg name>

What you're doing here is installing the packages under the super user rather than you the local user.

Upvotes: 2

Related Questions