Работа вокруг сельдерея, являющегося единственной точкой отказа

Я ищу рекомендуемое решение для обхода celerybeat, являющегося единственной точкой отказа для развертывания celery / rabbitmq. Пока что я не нашел ничего, что имело бы смысл, занимаясь поиском в Интернете.

В моем случае один раз в день планировщик запускает серию заданий, которые могут выполняться полдня или дольше. Поскольку может быть только один экземпляр celerybeat, если что-то случится с ним или с сервером, на котором он работает, критические задания не будут выполняться.

Я надеюсь, что уже есть рабочее решение для этого, поскольку я не могу быть единственным, кому нужен надежный (кластерный или подобный) планировщик. Я не хочу прибегать к какому-либо планировщику, поддерживаемому базой данных, если мне не нужно.

Ответы на вопрос(1)

работают ли они над этим все же.

В качестве обходного пути вы можете добавить блокировку для задач, чтобы одновременно выполнялся только 1 экземпляр определенного PeriodicTask.

Что-то вроде:

if not cache.add('My-unique-lock-name', True, timeout=lock_timeout):
    return

Выяснить тайм-аут блокировки хорошо, сложно. Мы используем 0,9 * task run_every секунд, если разные сельдереи будут пытаться запускать их в разное время. 0,9 только для того, чтобы оставить некоторую границу (например, когда сельдерей немного отстает от графика один раз, то он идет по графику, что приведет к тому, что блокировка все еще активна).

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

Задачи будут по-прежнему уважать run_every таким образом, в худшем случае: задачи будут выполняться с 0,9 * run_every скоростью.

Одна проблема в этом случае: если задачи были поставлены в очередь, но не были обработаны в запланированное время (например, из-за недоступности процессоров очереди) - блокировка может быть установлена в неправильное время, что может привести к тому, что 1 следующая задача просто не будет запущена. Чтобы обойти это, вам понадобится какой-то механизм обнаружения, является ли задача более или менее своевременной.

Тем не менее, это не должно быть обычной ситуацией при использовании в производстве.

Другим решением является создание подкласса планировщика сельдерея и переопределение его метода тиков. Затем для каждого тика добавьте блокировку перед обработкой задач. Это гарантирует, что только сельдереи с одинаковыми периодическими задачами не будут ставить в очередь одни и те же задачи несколько раз. Только один сельдерей для каждого тика (тот, кто победит в состоянии гонки) поставит в очередь задачи. В одном сельдерее происходит сбой, а в следующем тике победит другой.

Это, конечно, можно использовать в сочетании с первым решением.

Конечно, чтобы это работало, кеш-сервер должен быть реплицирован и / или совместно использоваться для всех серверов.

Это старый вопрос, но я надеюсь, что он кому-нибудь поможет.

Ваш ответ на вопрос