НейроАгент

Настройка cron каждые 10 секунд в CentOS 9 Stream

Решение проблемы с выполнением cron-задач каждые 10 секунд в CentOS 9 Stream. Альтернативные методы с systemd таймерами и сравнение с cron.

Вопрос

Как настроить выполнение cron-задачи каждые 10 секунд в CentOS 9 Stream? На CentOS 7 я использовал метод с несколькими записями в crontab с командой SLEEP, но в CentOS 9 Stream этот подход не работает - cron не выполняется и не пишет логи. Примеры текущих записей в crontab:

* * * * * sleep 0 ; /usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php >> /home/bitrix/.bx_temp/site.com/log/cron_events.log 2>&1
* * * * * sleep 10 ; /usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php >> /home/bitrix/.bx_temp/site.com/log/cron_events.log 2>&1
* * * * * sleep 20 ; /usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php >> /home/bitrix/.bx_temp/site.com/log/cron_events.log 2>&1
* * * * * sleep 30 ; /usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php >> /home/bitrix/.bx_temp/site.com/log/cron_events.log 2>&1
* * * * * sleep 40 ; /usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php >> /home/bitrix/.bx_temp/site.com/log/cron_events.log 2>&1
* * * * * sleep 50 ; /usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php >> /home/bitrix/.bx_temp/site.com/log/cron_events.log 2>&1

Какие альтернативные методы существуют для выполнения задач каждые 10 секунд в CentOS 9 Stream, и почему стандартный подход с SLEEP перестал работать?

НейроАгент

В CentOS 9 Stream стандартный подход с использованием нескольких записей в crontab и команды SLEEP перестал работать из-за изменений в системе управления службами и поведении cron. Основной альтернативой являются systemd таймеры, которые предоставляют более современный и надежный механизм выполнения задач с точностью до секунды.

Содержание

Проблема с SLEEP в CentOS 9 Stream

Стандартный подход, который использовался в CentOS 7 с несколькими записями в crontab и командой SLEEP, перестал функционировать корректно в CentOS 9 Stream. Как указывают исследования, cron изначально проектировался для запуска задач каждую минуту, и попытки об это ограничение с помощью SLEEP могут приводить к непредсказуемому поведению[source].

В вашем примере с шестью записями, каждая из которых использует команду sleep с задержкой 0, 10, 20, 30, 40 и 50 секунд, система в CentOS 9 Stream либо не выполняет задачи вовсе, либо не пишет логи, что указывает на изменения в работе cron-демона или связанных системных компонентов.

Почему старый метод не работает

Существует несколько причин, почему подход с SLEEP перестал работать в CentOS 9 Stream:

  1. Изменения в systemd: CentOS 9 Stream использует более новую версию systemd, которая по-разному управляет службами и таймерами по сравнению с CentOS 7[source].

  2. Ограничения cron: Как отмечается в исследованиях, cron не предназначен для выполнения задач с частотой более одной минуты в час, и все попытки обойти это ограничение являются “хакерскими”[source].

  3. Проблемы с синхронизацией: Исследования показывают, что команды sleep в cron могут иметь проблемы с синхронизацией, особенно при создании crontab файлов в определенное время[source].

  4. Изменения в поведении cron: В CentOS 9 Stream могут быть внесены изменения в то, как cron обрабатывает параллельные задачи или задачи с задержками.

Решение с использованием systemd таймеров

Наиболее надежным и современным решением для выполнения задач каждые 10 секунд в CentOS 9 Stream является использование systemd таймеров. Systemd таймеры предоставляют несколько преимуществ по сравнению с cron:

  • Точность до секунды: В отличие от cron, который ограничен минутной точностью, systemd таймеры позволяют указывать выполнение с точностью до секунды[source]
  • Надежность: Systemd таймеры гарантируют выполнение задачи, даже если система была выключена в запланированное время[source]
  • Управление зависимостями: Возможность указывать зависимости между службами и таймерами
  • Более продуманное управление параллельными задачами: Если задача занимает больше времени, чем интервал между запусками, systemd отложит следующий запуск, в отличие от cron, который может запустить несколько экземпляров задачи одновременно[source]

Создание systemd службы и таймера

Для выполнения вашего PHP-скрипта каждые 10 секунд создадим два файла: службу и таймер.

1. Создайте файл службы /etc/systemd/system/cron-events.service:

ini
[Unit]
Description=Run cron_events script every 10 seconds
After=network.target

[Service]
Type=simple
ExecStart=/usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php
User=bitrix
Group=bitrix
StandardOutput=file:/home/bitrix/.bx_temp/site.com/log/cron_events.log
StandardError=file:/home/bitrix/.bx_temp/site.com/log/cron_events.log

2. Создайте файл таймера /etc/systemd/system/cron-events.timer:

ini
[Unit]
Description=Run cron_events script every 10 seconds
Requires=cron-events.service

[Timer]
Unit=cron-events.service
OnUnitInactiveSec=10s
AccuracySec=1s

[Install]
WantedBy=timers.target

3. Активируйте и запустите таймер:

bash
systemctl daemon-reload
systemctl enable cron-events.timer
systemctl start cron-events.timer

4. Проверьте статус таймера:

bash
systemctl list-timers --all

Альтернативные методы выполнения задач каждые 10 секунд

Помимо systemd таймеров, существуют и другие альтернативные методы:

1. Использование while loop в отдельном скрипте

Создайте скрипт, который будет запускаться как systemd служба и содержать бесконечный цикл с задержкой:

bash
#!/bin/bash
while true; do
    /usr/bin/php -f /home/bitrix/ext_www/site.com/bitrix/php_interface/cron_events.php
    sleep 10
done

2. Использование anacron с измененной конфигурацией

Хотя anacron обычно предназначен для периодических задач с интервалами в дни, его можно настроить на более частые запуски, но это не является оптимальным решением для интервалов в 10 секунд.

3. Использование внешних инструментов

Можно рассмотреть использование специализированных инструментов для мониторинга и выполнения задач, таких как:

  • Supervisor: Для управления процессами
  • Runit: Для управления службами
  • Monit: Для мониторинга и автоматического запуска процессов

Настройка и управление systemd таймерами

Для более детальной настройки systemd таймеров можно использовать следующие параметры:

ini
[Timer]
# Запускать задачу каждые 10 секунд
OnUnitInactiveSec=10s

# Точность запуска (1 секунда)
AccuracySec=1s

# Случайная задержка для распределения нагрузки
RandomizedDelaySec=1s

# Максимальное время ожидания перед запуском
Persistent=true

# Запускать при загрузке системы
OnBootSec=10s

Для просмотра логов systemd таймеров используйте:

bash
journalctl -u cron-events.service -f

Для управления таймерами:

bash
systemctl stop cron-events.timer    # Остановить таймер
systemctl start cron-events.timer   # Запустить таймер
systemctl restart cron-events.timer # Перезапустить таймер
systemctl status cron-events.timer  # Проверить статус

Сравнение cron и systemd таймеров

Критерий Cron Systemd таймеры
Точность Минутная Секундная
Надежность Пропускает задачи при выключении системы Выполняет пропущенные задачи
Управление зависимостями Ограниченное Полное
Параллельные задачи Может запускать несколько экземпляров Откладывает следующий запуск
Конфигурация Простая, но ограниченная Более сложная, но мощная
Логирование Стандартные логи cron Интеграция с journalctl

Заключение

  1. Основная проблема: Подход с использованием нескольких записей в crontab и команды SLEEP перестал работать в CentOS 9 Stream из-за изменений в systemd и поведении cron.

  2. Оптимальное решение: Использование systemd таймеров предоставляет современный, надежный и точный механизм выполнения задач с интервалом в 10 секунд.

  3. Преимущества systemd: Точность до секунды, надежное выполнение пропущенных задач, лучшее управление параллельными задачами и интеграция с современной системой управления службами.

  4. Рекомендация: Для CentOS 9 Stream рекомендуется полностью перейти на systemd таймеры для высокочастотных задач, так как это более надежное и современное решение, которое будет лучше поддерживаться в будущих версиях системы.

  5. Дальнейшие шаги: При переходе на systemd таймеры рекомендуется также пересмотреть архитектуру задач, возможно, объединив несколько высокочастотных задач в одну более эффективную службу.