У меня возникла проблема с выполнением скрипта Python из PHP-скрипта. Мой клиент использует Bluehost, поэтому я установил сторонний модуль (numpy) для Python с помощью метода easy_install, описанного здесь: https://my.bluehost.com/cgi/help/530?step=530
Чтобы продемонстрировать свою проблему, я создал два сценария python и PHP-скрипт.
hello.py содержит:
print "Hello, World!"
hello-numpy.py содержит:
import numpy print "Hello, World!"
Сценарий PHP содержит:
Output from exec('python hello.py'): <?php echo exec('python hello.py'); ?><br> Output from exec('python hello-numpy.py'): <?php echo exec('python hello-numpy.py'); ?><br> Output from exec('whoami'): <?php echo exec('whoami'); ?>
Затем я получаю этот вывод из PHP:
Вывод из exec ('python hello.py'): Hello, World!
Вывод из exec ('python hello-numpy.py'):
Вывод от exec ('whoami'): venicetw
Однако запуск этих сценариев из окна SSH дает следующие результаты:
# python hello.py Hello, World! # python hello-numpy.py Hello, World! # whoami venicetw
Кажется, PHP не получает никакого вывода, когда скрипт Python импортирует numpy, но он отлично работает с SSH. Кроме того, PHP получает статус возврата 0 для hello.py, но 1 для hello-numpy.py. Я думал, что это может быть проблема с разрешениями, но как PHP, так и SSH работают как пользователь «venicetw». Что помешало бы PHP и Apache получить вывод из сценария Python? Это что-то, что я могу обсудить с Bluehost, или что-то еще, что я должен проверить? Мы используем Apache 2.2.21
, PHP 5.2.17
, Python 2.4.3
и numpy 1.6.0
.
Обновление: SSH печатает следующие пути Python:
/home8/venicetw/public_html/venicenoise/python /home8/venicetw/.local/lib/python2.4/site-packages/ogcserver-0.1.0-py2.4.egg /home8/venicetw/.local/lib/python2.4/site-packages/PIL-1.1.7-py2.4-linux-x86_64.egg /home8/venicetw/.local/lib/python2.4/site-packages/lxml-2.3.2-py2.4-linux-x86_64.egg /home8/venicetw/.local/lib/python2.4/site-packages/WebOb-1.2b2-py2.4.egg /home8/venicetw/.local/lib/python2.4/site-packages/PasteScript-1.7.5-py2.4.egg /home8/venicetw/.local/lib/python2.4/site-packages/PasteDeploy-1.5.0-py2.4.egg /home8/venicetw/.local/lib/python2.4/site-packages/Paste-1.7.5.1-py2.4.egg /home8/venicetw/.local/lib/python2.4/site-packages/numpy-1.6.0-py2.4-linux-x86_64.egg /home8/venicetw/.local/lib/python2.4/site-packages /home8/venicetw/.local/lib/python/site-packages /home8/venicetw/public_html/venicenoise/python /usr/lib64/python24.zip /usr/lib64/python2.4 /usr/lib64/python2.4/plat-linux2 /usr/lib64/python2.4/lib-tk /usr/lib64/python2.4/lib-dynload /usr/lib64/python2.4/site-packages /usr/lib64/python2.4/site-packages/Numeric /usr/lib64/python2.4/site-packages/PIL /usr/lib64/python2.4/site-packages/gtk-2.0 /usr/lib/python2.4/site-packages
Но Apache только печатает эти пути Python:
/home8/venicetw/public_html/venicenoise/python /usr/lib64/python24.zip /usr/lib64/python2.4 /usr/lib64/python2.4/plat-linux2 /usr/lib64/python2.4/lib-tk /usr/lib64/python2.4/lib-dynload /usr/lib64/python2.4/site-packages /usr/lib64/python2.4/site-packages/Numeric /usr/lib64/python2.4/site-packages/PIL /usr/lib64/python2.4/site-packages/gtk-2.0 /usr/lib/python2.4/site-packages
Решение: выполнив / usr / bin / env как с PHP, так и с SSH, я смог определить, что PHP не имеет переменной среды для пути Python, где установлен numpy. В этом случае, добавив
putenv('PYTHONPATH=/home8/venicetw/.local/lib/python2.4/site-packages:/home8/venicetw/.local/lib/python/site-packages:');
к началу PHP-скрипта все работает так, как ожидалось.
Если PHP получает статус возврата 1, это означает, что в процессе, который вы запустили, произошла ошибка. (Ненулевой статус выхода обычно указывает на ошибку в системах стиля Unix. Пара программ отличается, например, diff
.) Попробуйте изучить stderr
созданный подпроцессом, чтобы увидеть, какие сообщения об ошибках там печатаются.
Вы можете показать stderr
следующим образом:
Output from exec('python hello-numpy.py'): <?php echo exec('python hello-numpy.py 2>&1'); ?><br>
2>&1
инструктирует оболочку объединять stderr
и stdout
в один поток. Обычно вы не хотите этого делать, но это может облегчить просмотр ошибок.
Обновление. Поскольку ошибка, которую вы получаете, это ImportError: No module named numpy
мы можем попытаться найти пути Python. Возможно, в вашей системе установлено несколько Pythons, и также возможно, что среда Apache (корневой каталог и т. Д.) Отличается от среды, которую вы получаете при запуске Python через SSH. Попробуйте выполнить этот сценарий Python в обеих средах:
import sys, os for path in sys.path: print path print print 'Root:', os.readlink('/proc/self/root') # Linux only
Один из этих путей должен указывать на то, где установлен numpy
, и, возможно, он отсутствует при запуске в Apache. Или, возможно, процесс Apache имеет другой корневой каталог, который будет наследоваться процессом Python.
Решение: Отсутствует переменная среды. См. Комментарии.