首页 > 编程语言 >Django Celery配置踩坑:celery.py位置与队列选Redis还是数据库?

Django Celery配置踩坑:celery.py位置与队列选Redis还是数据库?

来源:互联网 2026-07-23 08:07:15

配置Celery时,需将Celery配置文件celery.py与Django设置文件settings.py放在同一目录,并在包初始化文件__init__.py中导入应用app。使用Redis作为消息代理和结果后端存储。在Windows系统上,必须安装eventlet库,并以-Peventlet参数启动Celery工作进程,否则任务将无法执行,导致队列堵塞。

个人在学习和使用Celery时,确实踩了不少坑,把过程中遇到的问题和解决办法整理下来,既方便自己回顾,也希望能帮到其他同学。

一、环境准备

  • Django 4.1.5
  • celery 5.4.0
  • redis 4.5.1
  • django-celery-results 2.5.1

其他项目需要的安装包,根据自己情况自行安装就好。

二、celery的配置

先来看 celery.py 文件内容:

长期稳定更新的攒劲资源: >>>点此立即查看<<<

from __future__ import absolute_import, unicode_literals
import os
from celery import Celery
from django.conf import settings

# 设置Django的settings模块
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'testplatform.settings')

app = Celery('testplatform')

# 使用Django的settings文件来配置Celery
app.config_from_object('django.conf:settings', namespace = 'CELERY')

# 自动从所有已注册的Django app中加载任务
app.autodiscover_tasks(lambda: settings.INSTALLED_APPS)


@app.task(bind = True)
def debug_task(self):
    print(f'Request: {self.request!r}')

这段代码网上到处都能抄到,没什么好说的。但接下来的几个坑,才是真正让人头大的地方。

坑一:

celery.py 文件必须放在和 settings.py 同一级目录下,千万别放到项目最外层的根目录。如果放错了位置,会出现以下问题:

  • 如果文件名就叫 celery.py,那么导入 from celery import Celery 时,会和自己写的文件冲突,直接报错。
  • 如果换个名字,比如 celeryConfig.py(内容不变),虽然不冲突了,但后续启动服务时又会冒出各种莫名其妙的问题,让人崩溃。

坑二:

celery.py 同级的 __init__.py 文件中,必须引入 app(也就是 Celery 创建的实例):

from .celery import app

如果不写这行,后面在视图函数里就没法用 @shared_task 装饰器,只能用 @app.task。而 @shared_task 本质上就是 @app.task 的一个快捷方式,但少了这步,它就是死活不认,实在让人摸不着头脑。

接下来是 settings.py 里的坑。

坑一:broker 和 result backend 的配置

刚开始问文心一言,它告诉我 CELERY_RESULT_BACKEND="django-celery-results",结果启动就失败了。后来又改成 CELERY_RESULT_BACKEND="django-db",虽然能启动,但任务根本不执行。最后走了一圈弯路发现,最稳妥的做法是把任务队列和结果队列都指向 Redis:

CELERY_BROKER_URL = f'redis://:{REDIS_PW}@{REDIS_IP}:{REDIS_PORT}/0'  # Redis数据库地址
CELERY_RESULT_BACKEND = f'redis://:{REDIS_PW}@{REDIS_IP}:{REDIS_PORT}/1' 
CELERY_ACCEPT_CONTENT = ['application/json']
CELERY_TASK_SERIALIZER = 'json'
CELERY_RESULT_SERIALIZER = 'json'
CELERY_TIMEZONE = 'Asia/Shanghai'  # 根据需要调整时区
CELERY_BROKER_CONNECTION_RETRY_ON_STARTUP = True

坑二:INSTALLED_APPS 里的 django_celery_results

在排雷过程中,发现网上有人建议在 INSTALLED_APPS 中加入 "django_celery_results"。我试了一下,发现不写也完全没影响,根本用不上。所以这里可以不用加:

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'app01.apps.App01Config',
    # 'django_celery_results'  # 可不加
    ]

视图函数和异步任务本身没什么好讲的,网上都有现成的例子。这里贴一下我练习时用的代码:

@csrf_exempt
def reset_data_api(request):
    # 调用异步任务
    result = reset_data.delay()
    task_id = result.task_id
    return JsonResponse({'status': True, 'data': {'message': '任务开始执行', 'task_id': f'{task_id}'}})

@shared_task
def reset_data():
    logger.info('开始执行任务')

    result = {
        "a": 123,
        "b": 456
        }
    logger.info('结束执行任务')
    return result

三、celery的运行

遇到最大的坑!!!!

很难想象,Celery 服务启动正常,任务消息也能收到,Redis 服务也是正常的,没有任何报错信息,但异步任务就是不执行,存放结果的队列里始终没有数据。搞了大半天,觉都睡不好,就是想不明白。

问文心一言,完全找不到原因,各种排查。最后在百度上搜到,才发现问题所在:

Celery 在 Windows 下运行有坑,需要借助 gevent、eventlet 等才能实现正常功能。解决方案是:

先 pip 安装 eventlet,然后运行 celery 时加上 -P eventlet 参数就行了。

Django Celery配置踩坑:celery.py位置与队列选Redis还是数据库?

Django Celery配置踩坑:celery.py位置与队列选Redis还是数据库?

基本上就这些了,后面使用过程中如果还有新坑,再继续补充~~

总结

以上是个人在实战中遇到的真实问题,希望能给大家一个参考,少走一些弯路。

侠游戏发布此文仅为了传递信息,不代表侠游戏网站认同其观点或证实其描述

热游推荐

更多
湘ICP备14008430号-1 湘公网安备 43070302000280号
All Rights Reserved
本站为非盈利网站,不接受任何广告。本站所有软件,都由网友
上传,如有侵犯你的版权,请发邮件给xiayx666@163.com
抵制不良色情、反动、暴力游戏。注意自我保护,谨防受骗上当。
适度游戏益脑,沉迷游戏伤身。合理安排时间,享受健康生活。