2024-12-29 14:51:33 +10:00

48 lines
1.6 KiB
Python

from celery.schedules import crontab
import logging
from allianceauth.framework.models import CronOffset
from django.db import ProgrammingError
logger = logging.getLogger(__name__)
# CELERYBEAT_SCHEDULE['marketmanager_fetch_public_market_orders'] = {
# 'task': 'marketmanager.tasks.fetch_public_market_orders',
# 'schedule': crontab(minute=0, hour='*/3'),
# }
def offset_cron(schedule: crontab) -> crontab:
"""Take a crontab and apply a series of precalculated offsets to spread out tasks execution on remote resources
Args:
schedule (crontab): celery.schedules.crontab()
Returns:
crontab: A crontab with offsetted Minute and Hour fields
"""
try:
cron_offset = CronOffset.get_solo()
new_minute = [(m + (round(60 * cron_offset.minute))) % 60 for m in schedule.minute]
new_hour = [(m + (round(24 * cron_offset.hour))) % 24 for m in schedule.hour]
# Type hints are fine here, crontab _expand_cronspec handles sets, the hinting is old
return crontab(
minute=",".join(str(m) for m in sorted(new_minute)),
hour=",".join(str(h) for h in sorted(new_hour)),
day_of_month=schedule._orig_day_of_month,
month_of_year=schedule._orig_month_of_year,
day_of_week=schedule._orig_day_of_week)
except ProgrammingError as e:
# If this is called before migrations are run hand back the default schedule
# These offsets are stored in a Singleton Model,
logger.error(e)
return schedule
except Exception as e:
# We absolutely cant fail to hand back a schedule
logger.error(e)
return schedule