как из python.py запустить скрипт оболочки shell с sudo правами
Есть реальная насущная задача для логирования сервера. Когда новые файлы логов создаются с владельцем от имени вебсервера, а не текущего пользователя системы, на которые они расчитаны. Логи будут находиться допустим в каталоге logs/ и создаваться будут через приложение loguru, которое нужно установить через pip.
В моём примере задача усложняется тем, что окружение python запускается на вебсервере apache2 через демона WSGI, поэтому потребуется использовать абсолютные пути и повозиться с правами. Поэтому файл операционной системы /etc/sudoers тоже требуется подправить, указав какой скрипт можно запускать с правами sudo без ввода пароля администратора.
значит в /etc/sudoers добавлена запись:
☯
Terminal:
⌕
≡
✕
username@itdid:~ $ cat /etc/sudoers username ALL=(ALL) NOPASSWD: /var/www/html/django_project/shell_script.sh www-data ALL=(ALL) NOPASSWD: /var/www/html/django_project/shell_script.sh
где username пользователь в системе от которого работает скрипт python.
допустим нам нужно запустить shell_script.sh внутри python скрипта на выполнение, со следующим содержимым(абсолютные пути обязательно):
shell_script.sh:
☯
Terminal:
⌕
≡
✕
username@itdid:~ $ cat /var/www/html/django_project/shell_script.sh #!/bin/bash /usr/bin/chown -R username:www-data /var/www/html/django_project/logs /usr/bin/chmod -R g+w /var/www/html/django_project/logs
Сам скрипт shell_script.sh после создания содержимого, обязательно стоит защитить от записи(chmod a-w) и удаления(chmod a+t), полностью.
☯
Terminal:
⌕
≡
✕
username@itdid:~ /var/www/html/django_project$ ls -la total 652 drwxrwxr-x 26 username www-data 4096 Mar 8 14:51 . drwxr-xr-x 6 username www-data 4096 Feb 23 17:15 .. -r-xr-xr-t 1 username username 368 Mar 4 18:14 shell_script.sh
теперь напишем скрипт для питона
python_script.py
☯
Terminal:
⌕
≡
✕
username@itdid:~ /var/www/html/django_project$ cat python_script.py import os from pathlib import Path import subprocess BASE_DIR = Path(__file__).resolve().parent.parent command = ['sudo', os.path.join(BASE_DIR, 'shell_script.sh')] # Open a subprocess and wait for it to complete proc = subprocess.Popen(command, stdout=subprocess.PIPE, stderr=subprocess.PIPE) # Wait for the subprocess to complete and get the output out, err = proc.communicate() #собственно и всё, фактически мы выполнили sudo shell_script.sh #если в окружении был установлен loguru, то сразу залогируем процесс from loguru import logger logger.add(os.path.join(BASE_DIR, 'logs/ loguru_info.log'),rotation="12:00",compression="zip", format="{time} {module} {message}", level="INFO")
logger.add(os.path.join(BASE_DIR, 'logs/loguru_debug.log'),rotation="12:00",compression="zip", format="{time} {module} {message}", level="DEBUG")
logger.add(os.path.join(BASE_DIR, 'logs/loguru_error.log'),rotation="12:00",compression="zip", format="{time} {module} {message}", level="ERROR") logger.debug('out {}',out) logger.debug('err {}',err)
-
- Roman Sakhno
Комментарии (0):
Для добавления комментариев надо войти в систему.
Если Вы ещё не зарегистрированы на сайте, то сначала зарегистрируйтесь.