
Я задаю этот вопрос после того, как по-королевски уничтожил коробку Linux. Позвольте мне рассказать вам немного предыстории, чтобы вы знали, откуда я пришел.
В настоящее время у меня есть (ну... был) RedHat Linux box, на котором запущен Apache с Phusion Passenger, добавленным для запуска приложений Ruby под Apache. Приложение действует как сервис для регулярной доставки кэшированных файлов киоскам в районе Цинциннати. Веб-приложение работало отлично, и единственное, что осталось, — настроить задачу cron для извлечения всей информации, которую нужно было кэшировать, и упаковать ее в несколько различных пакетов обновлений для доставки киоскам. Для этого я написал скрипт Ruby, который будет обрабатывать извлечение и упаковку данных. Для настройки задачи cron я просто использовал встроенный crontab. Скрипт выглядел так:
#!/bin/bash
cd ../lib
ruby pdf_cache.rb
ruby pdf_prepare.rb
ruby rss_cache.rb
ruby nightly-pack.rb
cd ..
chown -R www.www *
Этот скрипт находился в папке cron, а структура каталогов выглядела следующим образом:
.
|-- cron
|-- feeds
|-- lib
| `-- trash
|-- logs
|-- nightly-packs
|-- pdf
| `-- tank
|-- public
`-- tmp
и я запустил crontab -e
со root
следующим содержимым:
0 3 * * * /usr/local/apache2/ruby_projects/kiosk/cron/schedule_job
Который должен выполнять скрипт каждый день в 3 часа ночи. На следующий день после планирования этой задачи cron я получил очень неприятный сюрприз. Задача cron была выполнена в корне, и я предполагаю, что большинство команд не удалось выполнить, за исключением той, chmod -R www.www *
которая изменила владельца всего в системе на www
пользователя.
Мой вопрос: как правильно реализовать cron-задачу и из какого контекста запускается cron-задача? Теперь я понимаю, что, вероятно, не следует запускать это под учетной записью root
, и я не уверен, как запустить это под учетной записью, www
поскольку у этого пользователя нет оболочки, и вы не можете успешно подключиться su
к www
пользователю.
решение1
Держу пари, что вы могли бы просто предоставить пользователю оболочку, просто ограничить возможность удаленного доступа к ней и ее разрешения.
Задачи Cron выполняются от имени пользователей, создавших задачу Cron, поэтому она запускается как root
.
решение2
Еще одно предложение: добавьте -e
к строке shebang в скриптах вроде этого (т. е. #!/bin/bash -e
). Это заставит скрипт выйти, если любая команда в нем не сработает. Это не гарантирует, что у вас не будет неприятных сюрпризов, но это не даст скрипту полностью сойти с рельсов (так сказать), и предотвратит множество видов цепной реакции сбоев.
решение3
Правильный способ сделать это — 'su - ', настроить cronjob как этого пользователя. Тогда он будет работать от имени этого пользователя. Или, в зависимости от того, какой cron daemon вы используете, он может иметь 6-е поле для определения пользователя.
Надеюсь, это поможет. Есть и другие хаки, но всегда лучше заставить все работать правильно.