Как сценарий sh может определить, был ли он запущен как задание cron, а не как интерактивный или фоновый?
Я хотел бы использовать один и тот же сценарий для cron и Interactive, просто задаваясь вопросом, существует ли универсальный способ в системах UNIX/Linux, чтобы легко сделать это определение.
3 ответа
Вы можете попытаться вернуть имя родительского процесса примерно так:
ps -ocommand= -p $PPID | awk -F/ '{print $NF}' | awk '{print $1}'
Для меня это вернуло консоль, когда я запустил это в интерактивном режиме.
или вы можете написать скрипт в некоторой логике для обработки ситуаций.
while getopts cm opt
do
case $opt in
c)
## Do crontask
;;
m)
## Do manual
;;
esac
done
Теперь при выполнении скрипта вы можете передать опцию в качестве атрибута, например, так:
/use/local/bin/example.sh -m
/use/local/bin/example.sh -c
Универсального пути нет вообще. использование интерактивного / неинтерактивного обнаружения оболочки или tty-обнаружения также ненадежно, так как другие характеристики, кроме cron, могут иметь эти характеристики. просто добавьте переменную в вашу запись cron. скажем, вам нужно запустить test.sh, а затем использовать это вместо.
$ RUNENV=cron ./test.sh
cron
cat ./test.sh
#!/bin/sh
echo $RUNENV
Это довольно просто и надежно, если вы управляете настройкой cron.
Я не знаю, насколько это переносимо, но в Linux вы можете запустить tty
и проверьте, является ли вывод tty.
$ tty
/dev/pts/2
$ crontab -e
* * * * * echo $(tty) >> /home/paulo/cron_tty
[Wait a minute...]
$ cat /home/paulo/cron_tty
not a tty
Обратите внимание, что tty также не будет установлен, если скрипт выполняется неинтерактивно с чем-то другим, кроме cron, но, поскольку вы сказали, что хотите отличить cron от интерактивного, это не должно быть проблемой.
Кроме этого, возможно, наиболее надежное решение - добавить переключатель в ваш скрипт, сообщив ему, запущен ли он из cron или нет, как предложено в вопросе переполнения стека.