V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
V2EX 提问指南
no13bus
V2EX  ›  问与答

关于 django 和 celery 执行定时任务的问题。

  •  
  •   no13bus · 2014-07-15 16:47:59 +08:00 · 10903 次点击
    这是一个创建于 3544 天前的主题,其中的信息可能已经有所发展或是发生改变。
    网站基本框架就是有2个定时任务。第一个定时任务会从mysql里面根据当前登录用户id取得其数据表A里面的值,然后进行一些逻辑计算,然后发起网络请求。第二个定时任务也是这样,只是要将计算结果存入mysql数据库。
    django项目的结构和这里的一样。项目名称是proj 。app名称是demoapp
    http://docs.celeryproject.org/en/latest/django/first-steps-with-django.html#using-celery-with-django
    settings.py 里面加了下面的代码
    from datetime import timedelta
    CELERYBEAT_SCHEDULE = {
    'add-every-30-seconds': {
    'task': 'tasks.add',
    'schedule': timedelta(seconds=6),
    'args': (1,2)
    },
    }
    celery的broker和backend都是用的redis。
    然后运行celery -A proj worker -l info开启队列
    然后运行celery -A proj beat开启定时任务。
    但是开启定时后,总是说我Received unregistered task of type 'tasks.add'.
    难道是我setting里面的设置问题吗?我没有用django-celery
    21 条回复    2014-07-17 08:30:56 +08:00
    guoqiao
        1
    guoqiao  
       2014-07-15 17:05:37 +08:00 via iPhone   ❤️ 1
    定时任务直接用cron做最方便
    no13bus
        2
    no13bus  
    OP
       2014-07-15 17:09:56 +08:00
    我在python manage.py shell里面手动执行的时候 是可以执行任务队列的,但是celery -A proj beat开启定时任务就是说我没有注册任务
    no13bus
        3
    no13bus  
    OP
       2014-07-15 17:11:44 +08:00
    @guoqiao 你说的是celery里面的cron吗?还是linux自己的cron?他能借助dj的orm操作数据库吗?
    no13bus
        4
    no13bus  
    OP
       2014-07-15 17:14:43 +08:00
    @guoqiao 主要是还要和dj的数据库以及当前登录用户的信息进行交互。
    messense
        5
    messense  
       2014-07-15 17:14:56 +08:00   ❤️ 1
    用 Linux 自带的 crontab 比 Celery 的要精准得多吧。
    no13bus
        6
    no13bus  
    OP
       2014-07-15 17:20:41 +08:00
    @messense crontab不知道怎么和django交互。就用celery得了。现在就是发愁为什么说我注册不了那个tasks。以及django怎么和celery交互数据库。
    20150517
        7
    20150517  
       2014-07-15 17:21:58 +08:00   ❤️ 1
    正常,就是因为你没用celery版django才出这个的错误的
    qdvictory
        8
    qdvictory  
       2014-07-15 17:24:32 +08:00   ❤️ 1
    messense
        9
    messense  
       2014-07-15 17:27:03 +08:00
    @no13bus 写个 management command 提交任务给 celery 就行了。交互数据库和直接在 Django 中调用没什么差别吧。

    按照官方文档,设置好 DJANGO_SETTINGS_MODULE 应该就可以了吧。

    https://github.com/celery/celery/blob/3.1/examples/django/proj/celery.py
    aggron
        10
    aggron  
       2014-07-15 17:36:27 +08:00 via Android   ❤️ 1
    CELERYBEAT_SCHEDULE放在tasks.py中,
    app.conf.update(
    CELERYBEAT_SCHEDULE=...
    )
    没用过django-celery
    no13bus
        11
    no13bus  
    OP
       2014-07-15 17:39:28 +08:00
    @messense
    @qdvictory
    @20150517 你说的是django-celery这个插件吗?我在python manage.py shell里面手动执行的时候 是可以执行任务队列的,但是celery -A proj beat开启定时任务就是说我没有注册任务。我基本上就是按照https://github.com/celery/celery/blob/3.1/examples/django/proj/celery.py来配置的。只是改了app = Celery('btcproject',broker='redis://localhost:6379/0',backend='redis://localhost')

    这个是我的settings
    https://gist.github.com/no13bus/7500b6bfe7a4d9e1bbc3
    是settings的问题?
    ernest
        12
    ernest  
       2014-07-15 18:57:32 +08:00 via Android
    wibile
        13
    wibile  
       2014-07-15 19:45:39 +08:00   ❤️ 1
    应该不是setting问题,运行celery -A proj worker -l info看注册的tasks,是否和你beat里的一致,注意是个字符串,不同运行目录会注册不同的tasks名称,如:tasks.add或者xxx.tasks.add。
    no13bus
        14
    no13bus  
    OP
       2014-07-15 20:56:52 +08:00
    @wibile xxx.tasks.add settings里面改成这样的就对了 xxx是dj的app的名称
    no13bus
        15
    no13bus  
    OP
       2014-07-16 09:36:05 +08:00
    @guoqiao
    @messense
    @qdvictory
    你们用过celery的监控flower吗?昨天试验着安装完了。用celery -A proj flower 执行没反应。说celery没有这个命令
    no13bus
        16
    no13bus  
    OP
       2014-07-16 09:42:16 +08:00
    @qdvictory
    @messense
    你们的意思是在manage里面写自己的命令。然后 python manage.py mycommand在终端上执行吧。这样在自己写的脚本里面就能操作数据库了。然后使用crontab来定时执行刚才那句话。就不能用celery执行定时任务了吧。因为celery定时任务的话也是在终端上输入命令执行的。
    messense
        17
    messense  
       2014-07-16 09:50:13 +08:00
    @no13bus crontab 自己就是个定时任务嘛,而且系统级的精确度上应该也更高些,crontab 提交任务给 celery,celery 只要去执行就行了不用考虑定时的问题。
    guoqiao
        18
    guoqiao  
       2014-07-16 14:06:02 +08:00
    @no13bus 自然没问题
    先在app里写一个management command, 例如foo.py.
    在这里面你可以随意操作django ORM.
    然后在linux的crontab里, 定时执行这个command:

    0 4 * * * python /path/to/proj/manage.py foo

    如果有虚拟环境, 则指定python路径即可:

    0 4 * * * /path/to/venv/bin/python /path/to/proj/manage.py foo
    no13bus
        19
    no13bus  
    OP
       2014-07-16 15:59:58 +08:00
    @guoqiao 多谢了。我用celery做的,操作数据库写在了tasks.py里面了。然后再终端运行celery命令即可。
    messense
        20
    messense  
       2014-07-17 08:11:41 +08:00
    @no13bus 试了下 flower,运行没有问题啊。
    no13bus
        21
    no13bus  
    OP
       2014-07-17 08:30:56 +08:00 via Android
    @messense 我知道了,解决了,是tornado版本太低,2.2,改成3就好了
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   我们的愿景   ·   实用小工具   ·   3258 人在线   最高记录 6543   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 27ms · UTC 11:30 · PVG 19:30 · LAX 04:30 · JFK 07:30
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.