TrMax
TrMax

Reputation: 77

How to execute shell_exec on EC2 Linux

I am running an API on a EC2 Linux instance. I try to to execute a Python script from a PHP file. The path to the PHP file is /var/www/html/droptop/api/event/test.php. The path to the Python script is /var/www/html/droptop/blacklist/profanity.py. The Python script recieves two strings and checks whether one of these two strings contain objectionable content via Profanity Check. Then it returns 0 if no objectionable content was found, otherwise it returns 1. However, shell_execalways seems to return NULL. Profanity Check needs Python 3 to work properly.

When executed on command line, the PHP file and Python script perfectly work fine together.

I assume it has something to do with the user's permissions. apache and not www-data user is executing the files. However, I also changed the sudoers file according to here. I included following lines:

apache ALL=NOPASSWD:/var/www/html/droptop/blacklist/profanity.py
apache ALL=NOPASSWD:/usr/bin/python3.6

I also checked if apache is part of groups which it is.

I also tried other functions like exec(), system() or passthru().

Still it always returns NULL.

test.php

$command = escapeshellcmd('python3 /var/www/html/droptop/blacklist/profanity.py Some BadWord');
$output = shell_exec($command);

if($output == 0) {
  echo json_encode(array("message" => "No Badword found."));
}

profanity.py

#!/usr/bin/python36

from profanity_check import predict, predict_prob
import sys

# get title
title = sys.argv[1]
pred_title = predict([title])
pred_details = 0

if(len(sys.argv) == 3):
    details = sys.argv[2]
    pred_details = predict([details])

if((pred_title == 0) and (pred_details == 0)):
    print(0)
else:
    print(1)

What could be the problem here?

Upvotes: 1

Views: 1313

Answers (2)

sivi
sivi

Reputation: 11114

Try check the error logs The server access point to the web is controlled by the web server It could be that there are permission issue to the file you want to write. For example I was trying to write to a file owned by "user" but apache "www-data" has no permission check the error logs inside:

/var/log/apache2

They may be instructive into seeing what is the real problem.

Upvotes: 0

HTF
HTF

Reputation: 7260

You should remove these sudoers entries, they shouldn't be necessary in your case and it's a security risk.

I would also recommend to not relay on the output and use the exit status instead:

test.php

<?php
$command = escapeshellcmd('python3 /var/www/html/droptop/blacklist/profanity.py Some BadWord');
exec($command, $output, $return_var);

//echo $output;

if(!$return_var) {
  echo json_encode(array("message" => "No Badword found."));
}
?>

profanity.py

import sys

from profanity_check import predict


def profanity(words):
    return predict(words)

def main():
    words = sys.argv[1:]
    ret = profanity(words)
    sys.exit(any(ret))

if __name__ == '__main__':
    main()

Now, back to your original issue, the docs says

This function can return NULL both when an error occurs or the program produces no output.

You can un-comment the //echo $output; line and assuming you're using Apache web server running as apache user you can try to run the command below, hopefully this will give you some clue:

$ runuser -l apache -s /bin/bash -c "php -f /var/www/html/droptop/api/event/test.php; echo"
{"message":"No Badword found."}

Possible issues:

  • your python installation is not in the $PATH for apache user

  • profanity_check module is not installed globally

Upvotes: 1

Related Questions