Предоставление обычным пользователям (без полномочий root) возможностей инициализации и автоматического запуска
Я размещаю экспериментальную / тестируемую коробку Linux с дистрибутивом Debian Wheezy 7.4.0. Различные пользователи подключаются к машине через ssh под своими учетными записями, и им разрешается запускать средства разработки и оставлять свои программы работающими в фоновом режиме, если они того пожелают.
Поскольку это тестирующий компьютер для самых разных целей, часто возникает необходимость перезапустить всю машину, а затем пользователям необходимо снова войти в систему и перезапустить свои работающие компоненты пользовательского пространства. Я хотел бы автоматизировать это. По сути, я хотел бы предоставить пользователям средство для запуска чего-либо сразу после загрузки машины (после того, как все остальное инициализировано) и средство для запуска чего-либо при завершении работы системы (без ограничений по времени, в основном, остановка до завершения всех этих остановок). пользовательские процессы завершены).
Что я уже пробовал:
Я создал скрипт init bash, следуя принципам, найденным в файле шаблона 'skeleton' в /etc/init.d/ (Исходный код шаблона Skeleton: https://gist.github.com/ivankovacevic/9917139)
Мой код здесь: https://github.com/ivankovacevic/userspaceServices
По сути, скрипт просматривает домашние каталоги пользователей и ищет исполняемые файлы в соответствующих подкаталогах с именами.startUp,.shutDown или.status. В зависимости от события, которое происходит в данный момент, сценарии выполняются с su, как если бы пользователи запускали их сами.
Проблема, с которой я сейчас сталкиваюсь при таком подходе, заключается в том, что после загрузки системы происходит странный процесс, и скрипт запускает все процессы других пользователей. Вот как это выглядит в списке процессов:
UID PID PPID C SZ RSS PSR STIME TTY TIME CMD
root 3053 1 0 1024 620 1 17:42 ? 00:00:00 startpar -f -- userspaceServices
Я не знаю, что это за процесс, и на странице руководства для него не упоминается аргумент -f. Так что я ничего не понимаю, но, должно быть, я делаю что-то не так, поскольку никакой другой скрипт / сервис из init.d не оставляет такой процесс зависшим после загрузки.
Поэтому я ищу кого-то, чтобы помочь мне отладить это решение, которое у меня есть (что также кажется немного сложным, на мой взгляд). Или дайте мне некоторое представление о том, как это можно реализовать совершенно по-другому.
ОБНОВИТЬ
Я начал отдельный вопрос для проблемы startpar: процесс startpar зависал при запуске процессов из rc.local или init.d
ОБНОВЛЕНИЕ 2
Проблема решена для моего оригинального решения. Проверьте ранее упомянутый вопрос для startpar. Код на GitHub также исправлен, чтобы отразить это.
ОБНОВЛЕНИЕ 3 - Как использовать crontab
Как предложила Дженни, обычные пользователи могут планировать выполнение задач один раз при загрузке с помощью crontab. Я считаю, что это самый простой способ, если все, что вам нужно, это запускать пользовательские задачи при загрузке, а не завершать работу. Однако существует недостаток, заключающийся в том, что пользователи могут оставлять процесс cron "зависшим" как родительский, когда они запускают текущие, подобные сервису задачи. Сначала позвольте мне объяснить, как это работает:
Сами обычные пользователи должны звонить:
crontab -e
(-e как в редактировании), который открывает консольный текстовый редактор по умолчанию с их пользовательским файлом crontab. Чтобы добавить задачу для выполнения при загрузке, пользователь должен добавить одну строку в конце файла:
@reboot /path/to/the/executable/file
Теперь, если пользователь сделает именно это, и если этот файл не просто какой-то простой скрипт, который что-то линейно завершает и завершает, а, например, какой-то сторожевой таймер, например, после перезагрузки вы закончите что-то вроде этого в вашем списке процессов:
1 2661 root 20 0 20380 860 660 S 0.0 0.0 0:00.00 ├─ /usr/sbin/cron
2661 2701 root 20 0 33072 1152 868 S 0.0 0.0 0:00.00 │ └─ /USR/SBIN/CRON
2701 2944 someuser 20 0 4180 580 484 S 0.0 0.0 0:00.00 │ └─ /bin/sh -c ./watchdog
2944 2945 someuser 20 0 10752 1204 1016 S 0.0 0.0 0:00.00 │ └─ /bin/bash ./watchdog
2945 2946 someuser 20 0 23696 4460 2064 S 0.0 0.1 0:00.01 │ └─ /usr/bin/python ./some_program.py
Чтобы избежать этого, пользователь должен изменить свою запись в crontab так:
@reboot /path/to/the/executable/file >/dev/null 2>&1 &
Перенаправление файловых дескрипторов не является обязательным, но рекомендуется поддерживать его в чистоте. Если вы хотите изучить почему, попробуйте посмотреть на них:
ls -l /proc/pid_of_started_process/fd
1 ответ
Я согласен, что ваше решение кажется немного сложным, поэтому я пойду с "дать мне некоторое представление о том, как это может быть реализовано совершенно по-другому":-)
Стандартным решением для этого является использование системы управления конфигурацией, такой как puppet, и предоставление пользователям возможности добавлять свои данные в конфигурацию puppet для сервера. Затем Puppet вытолкнет стартовый скрипт и добавит их в соответствующие уровни запуска.
Более быстрый способ - дать им доступ к
/etc/rc.d/rc.local
и добавьте свои вещи туда.Или дайте каждому из них каталог для размещения стартовых скриптов, которые они хотят запустить, и поручите заданию cron скопировать эти скрипты в
/etc/init.d
, вставивsu $USER -c
в подходящих местах и запустите на них команду chkconfig.Или дайте им каждый каталог для размещения стартовых скриптов и добавьте несколько строк в конце
/etc/rc.d/rc.local
пройти через эти каталоги и запустить отредактированныйsu $USER -c 'script start'
на каждом скрипте в них.
Отредактировано, чтобы добавить:5. Позвольте им использовать crontab, чтобы запланировать выполнение заданий @reboot