Мне нужно предотвратить одновременное выполнение сценария несколько раз, поэтому flock
кажется прямо на моей улице.
Что я не могу понять, так это то, нужно ли мне вручную удалить файл блокировки после завершения задания cron?
Я использую это так:
# m h dom mon dow user command
*/20 * * * * root /usr/bin/flock -w 0 /var/cron.lock /usr/bin/myscript
Этот сценарий также выполняется выскочкой при запуске машины (здесь и возникает состояние гонки).
Файл создан нормально, но я не могу понять, как команда узнает, удерживается ли блокировка другим процессом. Он пуст, и отслеживание изменений при запуске задания cron ничего не дает (использование fuser
).
Если кто-то может объяснить, как это работает, я был бы очень признателен!
Файл блокировки, указанный вами в качестве параметра для /usr/bin/flock
; /var/cron.lock
остается заблокированным flock(2)
системный вызов на время вашего скрипта /usr/bin/myscript
. Как только ваш скрипт завершится, эта блокировка снова будет снята /usr/bin/flock
.
Когда /usr/bin/flock
команда не может достичь блокировки, т.е. потому что /var/cron.lock
уже заблокирован, потому что ваш скрипт все еще запущен (или любое другое состояние ошибки), / usr / bin / flock не выполнит ваш скрипт. Ваш скрипт не нужно изменять и не нужно выполнять какую-либо проверку блокировки, все это выполняется / usr / bin / flock.
Сам файл блокировки будет создан как пустой файл /usr/bin/flock
команда, если она еще не существует, но после ее создания файл блокировки не изменяется, только flock (2) будет применен и удален. Файл не будет удален после завершения вашего скрипта.
По какой причине вы не можете сделать что-то вроде:
# m h dom mon dow user command
*/20 * * * * root (/usr/bin/pgrep myscript || /usr/bin/myscript)
Если процесс не может быть найден в таблице моментальных снимков текущего процесса, он возвращает 1 и выполняет /usr/bin/myscript
.
Если процесс можно найти в таблице моментальных снимков текущего процесса, он возвращает 0 и останавливает выполнение.