Сегодня, работая над внутренним проектом, я столкнулся с действительно интересной проблемой. Мне нужен был сценарий Python, работающий каждые 30 минут, извлекая некоторую информацию от третьей стороны, обрабатывая данные, обновляя мою локальную базу данных и отдыхает до следующего раунда. Я написал сценарий и настроил Cron.
Плавно!
Но мое счастье длилось недолго. Иногда мой скрипт занимал более 30 минут, чтобы выполнить. Это представило мне прекрасную проблему с перекрывающимися и дублированием данных Cron. Я не хотел, чтобы задания начали складываться друг на друга.
Ах. Милый параллелизм проблема.
Чтобы исправить это, как и любой другой разработчик, у меня появилась пара мыслей.
- Измените мой скрипт Python, используйте какой -нибудь внутренний пакет, чтобы перечислить все запуска процессов и Grep, если тот же Cron уже работает. Если да, возможно, это не хорошее время, чтобы запустить его.
- Почему бы не искать существование конкретного файла
mylock.txt
и выйдите, если он существует, или создайте его, если это не так?
Оба решения казались довольно паршивыми и небезопасными. И прикосновение к рабочему коду — мой самый большой кошмар.
Наша внутренняя дискуссия направила меня к красивому инструменту, Стая Анкет
Стая очень простой и простой инструмент. Эта крошечная утилита поступает по умолчанию с util-linux
упаковка.
Его механизм довольно аккуратный и простой. Для исполнения это требует Заблокировать файл
& Команда
запустить как вход. Он помещает блокировку в заданный файл блокировки и выпускает блокировку при выполнении скрипта. Заблокировать файл помогает инструменту решить, запустить ли сценарий или нет, в следующем раунде.
Просто чтобы добавить здесь, блокировка файла является механизмом ограничения доступа к файлу между несколькими процессами. Это позволяет только один процесс получить доступ к файлу в определенное время.
Как настроить задание Cron, используя стад?
Настройка Cron с помощью стада довольно проста.
Шаг 1 — Установите стад, Если нет в вашей системе
yum install -y util-linux
Вы можете проверить, был ли Flock установлен по где стечь
в системе Linux. Он должен показать /usr/bin/flock
как путь.
Шаг 2 — Откройте вкладку Cron
crontab -e
Шаг 3 — Установите свой новый Cron
*/30 * * * * /usr/bin/flock -w 0 /home/myfolder/my-file.lock python my_script.py
И все готово.
Момент начинается, он блокирует my-file.lock
Файл и если в следующем раунде, предыдущий Cron уже работает, он больше не будет сценарием.
Не беспокойся о my-file.lock
, Flock создаст его для вас, если его не существует.
Чтобы проверить блокировку, попробуйте —
fuser -v /home/myfolder/my-file.lock
Итак, моя запись Crontab выглядела так —
*/30 * * * * /usr/bin/flock -w 0 /home/myfolder/my-file.lock python my_script.py > /home/myfolder/mylog.log 2>&1
Ну, успокойся. Я знаю, я добавил несколько случайных текстов в свой крон. Давайте расшифруем значение >/home/myfolder/mylog.log 2> & 1
по одному.
>
это стандартное перенаправление ввода/вывода./Home/myfolder/mylog.log
черная дыра куда отправляются какие -либо данные2
Является ли дескриптор файла для стандартной ошибки (STDERR)>
, снова для перенаправления&
Символ для дескриптора файла1
Дескриптор файла для стандартного вывода (stdout)
2> & 1
означает перенаправление канала 2 (stderr) на канал 1 (stdout), поэтому оба выхода теперь находятся на одном канале 1. >/home/myfolder/mylog.log
Средства, вывод из канала 1 будет отправлен в эту черную дыру.
Подводя итог, что вывод и ошибки генерируются, когда выполнение вашего сценария перейдет в этот файл.
Несчастные истины стада
Как запустить несколько команд с помощью Flock
У меня был интересный вариант использования. Из-за некоторых системных абсолютных вещей, связанных с путем, внутри моего сценария Python, мне пришлось запустить сценарий в качестве комбинации двух команд.
Вместо —
python /home/myfolder/script.py
Мне нужно было сделать —
cd /home/myfolder/ && python script.py
Запускать несколько команд с помощью стада, немного сложно. После небольшой борьбы этот сработал для меня.
*/30 * * * * cd /home/myfolder/ /usr/bin/flock -w 0 /home/myfolder/my-file.lock && python my_script.py > /home/myfolder/mylog.log 2>&1
Стань, кажется, не всегда работает.
Стол делает Консультативная блокировка , которая является схемой блокировки кооператива, что означает, что вы сможете переопределить замок, если не сотрудничаете.
Много раз поднималось, что если стадо используется для вызова команды в подборке, другие программы, похоже, могут читать/записать в заблокированный файл. Эта проблема на Stackoverflow рассказывает об этом подробно.
Оригинал: «https://dev.to/pankajtanwarbanna/prevent-duplicate-cron-job-running-3i1e»