У меня есть сценарий PHP, который вызывается HTTP, а не сценарием командной строки. Этот сценарий должен вызывать команду оболочки от имени пользователя, отличного от www-data текущего пользователя веб-сервера.
Пример:
<?php
echo shell_exec('sudo -u myusername -S /usr/bin/whoami'); // returns nothing :(
echo shell_exec('whoami'); // returns www-data
При вызове этой 2 команды sudo -u myusername -S /usr/bin/whoami
и whoami
прямо в командной строке они возвращают
myusername
www-data
Также нет результата по этому поводу:
<?php
echo shell_exec('echo "mypass" | sudo -u myusername -S /usr/bin/whoami');
Мне кажется, что sudo вообще не работает вместе с PHP shell_exec ().
Во-первых, я не понимаю выполняемую вами команду sudo. sudo -u username
Предполагается, что вы, как пользователь номер один, можете выполнить sudo команду в качестве пользователя номер два, сказав (в качестве пользователя номер один, в этом примере, чтобы запустить команду ls):
sudo -u usertwo ls
Прошу прощения, если вы пытались дезинфицировать свои команды выше, заменив username
для настоящего имени пользователя, но я не могу быть уверен, что вы это сделали, поэтому сначала мне нужно поднять этот вопрос.
Во-вторых, необходимо настроить sudo, чтобы пользователь мог выполнять ряд команд от имени другого пользователя. Начнем с того, что разрешим www-data выполнять sudo команду ls от имени пользователя fribble; вы можете проверить это, поставив
www-data ALL = (fribble) NOPASSWD: ls
в вашем файле sudoers (подставив реального пользователя как fribble). Тогда попробуйте сделать, скажем, ls -la /tmp
изнутри вашего PHP-скрипта и посмотрите, получите ли вы список каталогов.
Я согласен с Джеймсом Лори в том, что не рекомендуется разрешать пользователю www-data выполнять произвольные команды sudo в качестве произвольных пользователей без пароля, но если вы уточните, какие команды вы пытаетесь запустить www-data, это может быть разумный способ сделать это.
Редактировать:
вы пробовали использовать ls в файле sudoers и sudo -u user2 ls -al /tmp
в сценарии PHP, и вы получите список каталогов, который убедительно свидетельствует о том, что sudo отлично работает с PHP.
Конечно, не могли бы вы позволить /bin/touch
в файле sudoers поместите sudo -u user2 touch /tmp/TESTFILE
в сценарии PHP, затем выполнить это? Если файл /tmp/TESTFILE
, принадлежащий пользователю user2, мы можем быть уверены, что sudo и PHP нормально работают вместе.
Должен признаться, что если бы я знал, что вы пытаетесь использовать sudo java, я бы никогда не ответил на исходный вопрос, потому что я думаю, что java - это гигантский непредсказуемый мешок дерьма, который ведет себя как полноценный ребенок, если он не получает среда, которую он требует (и sudo довольно строго очищает среду). Но, по крайней мере, приведенный выше тест должен помочь вам быть уверенным в том, что независимо от проблемы, это не проблема с PHP и sudo, которые не работают вместе.
Не разрешайте пользователю веб-сервера доступ к sudo, вы просто напрашиваетесь на проблемы. Вместо этого посмотрите на бит setuid:
chmod u+s some_file_that_needs_executing_as_another_user.pl
Каждый раз, когда этот файл выполняется, он будет эффективно выполняться пользователем, который его создал.
Кстати, я уверен, что вы не сможете передать пароль в sudo или passwd.
Если вы хотите предоставить особые разрешения процессу веб-сервера, запущенному как пользователь www-data, вы можете выполнить одно из следующих действий:
1- Добавьте www-data в файл sudoers, чтобы он мог выполнить необходимую команду / скрипт, не запрашивая пароль.
2- Включите модуль suexec apache. Это позволяет вам изменить пользователя с www-data на другого привилегированного пользователя для каждого виртуального хоста. Таким образом, вам не нужно менять пользователя для всего сервера.