芹菜击败 - 每个任务的不同时区

ksr*_*ini 2 python django django-celery celerybeat

我正在使用芹菜殴打来安排一些任务.我可以使用CELERY_TIMEZONE设置来使用crontab计划安排任务,并在上述时区的预定时间运行.

但我希望能够在同一个应用程序中为不同的时区设置多个此类任务(单个django settings.py).我知道在安排任务时需要在哪个时区运行哪个任务.

是否可以为每个任务指定不同的时区?

我正在使用django(1.4)和芹菜(3.0.11)和django芹菜(3.0.11).

我看过这个djcelery.schedulers.DatabaseScheduler类和它的基类,但我无法弄清楚时区的使用方式和位置.我可以编写一个自定义调度程序,可以使每个作业在不同的时区运行吗?

谢谢,

thm*_*hmp 10

您可以在芹菜计划中实现单个任务的时区感知计划.这样,您可以通过为每个芹菜计划指定一个单独的now函数,根据特定时区中的本地时间(也可以调整为夏令时)来运行任务

crontab支持nowfun参数以指定用于检查它是否应该运行的日期时间函数

import datetime
import pytz
nowfun = lambda: datetime.datetime.now(pytz.timezone('Europe/Berlin'))
Run Code Online (Sandbox Code Playgroud)

在您的日程表中,将此功能设置为日期时间功能

'periodic_task': {
    'task': 'api.tasks.periodic',
    'schedule': crontab(hour=6, minute=30, nowfun=nowfun)
}
Run Code Online (Sandbox Code Playgroud)

每天早上6点30分CET调整为夏令时.

如果您多次使用该功能,请考虑创建一个帮助程序

from functools import partial
cet_crontab = partial(crontab, nowfun=nowfun)
'periodic_task': {
    'task': 'api.tasks.periodic',
    'schedule': cet_crontab(hour=6, minute=30)
}
Run Code Online (Sandbox Code Playgroud)

确保您已CELERY_ENABLE_UTC = False设置,否则芹菜将您的日程表转换为UTC.

  • 这在 Celery 中不再有效,因为 nowfun 将无法 picklable。 (4认同)
  • @BrettJackson 为了 pickle `nowfun`,我将它声明为普通函数而不是 lambda,这很有帮助。 (4认同)
  • @JessicaRyan 在创建时转换时区不处理 DST 更改 (3认同)

And*_*bin 0

我认为最简单的方法是使用装饰器mock

from mock import patch

@task
@patch.multiple(settings, CELERY_TIMEZONE='time_zone')
def my_task(*args):
    #do your staff
Run Code Online (Sandbox Code Playgroud)

我还没有测试过,但它似乎是正确的。我希望我对你有帮助:)