Компонент планировщика Symfony... Заметка
DEV Community на русском

Компонент планировщика Symfony: Cron в вашем приложении, а не в вашем crontab

В статье обсуждается компонент Symfony Scheduler как современная альтернатива традиционным crontab для управления запланированными задачами в PHP-приложениях. В ней освещаются проблемы crontab, такие как привязка к хосту, нахождение вне системы контроля версий, а также сложность управления и тестирования. Symfony Scheduler переосмысливает повторяющиеся задачи как версионированный PHP-код, что позволяет проводить ревью кода и модульное тестирование.Ядром Scheduler является класс поставщика расписания, помеченный #[AsSchedule], который реализует ScheduleProviderInterface. Этот класс определяет, какие задачи должны выполняться и когда, используя либо удобочитаемые интервалы с помощью RecurringMessage::every(), либо стандартные cron-выражения с помощью RecurringMessage::cron(). Сами сообщения представляют собой обычные объекты передачи данных (DTO).Для cron-выражений требуется пакет dragonmantank/cron-expression, который предлагает функцию хешированных cron-выражений для распределения нагрузки и предотвращения одновременного запуска задач в одно и то же время. Scheduler использует компонент Symfony Messenger в качестве своей базовой системы, что означает, что запланированные сообщения проходят через те же промежуточные программы, стратегии повторных попыток и обработку сбоев, что и другие сообщения приложения.Задачи могут быть определены как сообщения с выделенными обработчиками или непосредственно в методах сервисов с использованием атрибутов #[AsCronTask] и #[AsPeriodicTask] для более простых, одноразовых операций. Значительным преимуществом Scheduler является его тестируемость; расписания можно тестировать модульно без необходимости загрузки полного приложения или ожидания выполнения. В статье предупреждается о критической ошибке: запуск нескольких процессов-потребителей Scheduler приведет к дублированию выполнения задач.Чтобы предотвратить это, транспорт Scheduler должен быть настроен с блокировкой, гарантирующей, что только один процесс генерирует запланированные сообщения. Эта блокировка должна опираться на общий репозиторий, такой как Redis. Для избыточности потребители могут масштабироваться горизонтально, но только один рабочий должен владеть блокировкой и выполнять планирование.Кроме того, Scheduler может быть сделан состоятельным с использованием общего пула кэша, что позволит наверстать упущенные задачи при перезапуске рабочего. В конечном итоге Symfony Scheduler выводит задачи планирования из инфраструктуры в код приложения, в соответствии с принципами децентрализованной архитектуры. Этот подход повышает поддерживаемость, сохраняя логику планирования версионированной, доступной для ревью и тестируемой в рамках кодовой базы приложения.
CdXz5zHNQW_ftlbF6BSQY.webp