我想要一个每5分钟执行一次的任务,但它会等待最后一次执行完成,然后开始计算这5分钟。 (这样我也可以确定只有一个任务在运行)我找到的最简单的方法是运行django应用程序manage.py shell并运行它:
while True:
result = task.delay()
result.wait()
sleep(5)
但是对于我想以这种方式执行的每个任务,我必须运行它自己的shell,有一个简单的方法吗?可能是一些国王定制django芹菜调度程序?
答案 0 :(得分:17)
令人惊讶的是,没有人理解这个人的问题。他们不是要求定期运行任务,而是如何确保Celery不会同时运行同一任务的两个实例。我认为没有办法直接用Celery做到这一点,但你可以做的是让其中一个任务在开始时获得锁定,如果失败,则在几秒钟内再次尝试(使用重试) 。任务将在返回之前释放锁定;如果崩溃或超时,您可以在几分钟后使锁自动过期。
对于锁定,您可以使用您的数据库或类似Redis的东西。
答案 1 :(得分:16)
您可能对这种简单的方法感兴趣,不需要更改芹菜配置。
@celery.decorators.periodic_task(run_every=datetime.timedelta(minutes=5))
def my_task():
# Insert fun-stuff here
答案 2 :(得分:12)
您需要的只是在celery conf witch任务中指定您想要定期运行以及在哪个时间间隔内运行。
示例:每30秒运行一次tasks.add任务
from datetime import timedelta
CELERYBEAT_SCHEDULE = {
"runs-every-30-seconds": {
"task": "tasks.add",
"schedule": timedelta(seconds=30),
"args": (16, 16)
},
}
请记住,您必须使用-B选项
以节拍模式运行芹菜manage celeryd -B
你也可以使用crontab样式而不是时间间隔,结帐:
http://ask.github.com/celery/userguide/periodic-tasks.html
如果您正在使用django-celery,请记住您也可以使用tha django db作为定期任务的调度程序,这样您就可以轻松地通过django-celery管理面板添加新的定期任务。 为此,您需要以这种方式在settings.py中设置celerybeat调度程序
CELERYBEAT_SCHEDULER = "djcelery.schedulers.DatabaseScheduler"
答案 3 :(得分:4)
从http://docs.celeryproject.org/en/v2.2.4/userguide/periodic-tasks.html
扩展@ MauroRocco的帖子对时间表使用timedelta意味着任务将在celerybeat启动后30秒执行,然后在最后一次运行后每30秒执行一次。还存在类似crontab的计划,请参阅有关Crontab计划的部分。
所以这确实会实现你想要的目标。
答案 4 :(得分:2)
由于不推荐使用celery.decorators,你可以像这样使用periodic_task装饰器:
from celery.task.base import periodic_task
from django.utils.timezone import timedelta
@periodic_task(run_every=timedelta(seconds=5))
def my_background_process():
# insert code
答案 5 :(得分:0)
将该任务添加到单独的队列,然后对该队列使用单独的worker,并将并发选项设置为1。