Django+Celery+SQS问题:Celery Worker接收消息但不执行任务
问题描述
我尝试在Django Web应用中使用Celery和AWS SQS作为消息代理实现后台任务。视图调用任务后,任务已成功发送至SQS,启动Celery Worker的控制台显示任务已接收,但实际任务从未执行(任务中的打印语句无输出)。
相关配置与代码
settings.py中的Celery配置
CELERY_ACCEPT_CONTENT = ['application/json'] CELERY_TASK_SERIALIZER = 'json' CELERY_TASK_DEFAULT_QUEUE = 'tk-test-queue' CELERY_BROKER_URL = "sqs://%s:%s@" % (quote(os.environ.get('AWS_ACCESS_KEY_ID'), safe=''), quote(os.environ.get('AWS_SECRET_ACCESS_KEY'), safe='')) CELERY_BROKER_TRANSPORT_OPTIONS = { 'region': 'ap-south-1', 'visibility-timeout': 60 * 30, 'polling_interval': 1 } CELERY_RESULT_BACKEND = None
celery.py内容
import os from celery import Celery os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'my_project.settings') app = Celery('my_project') app.config_from_object('django.conf:settings', namespace="CELERY") app.autodiscover_tasks()
my_app/tasks.py中的任务定义
from time import sleep, ctime from celery import shared_task @shared_task def export_report_to_s3(): print(f'Starting task at {ctime()}') sleep(25) print(f'Task finished at {ctime()}')
my_app/views.py中的任务调用
class TestCeleryView(View): def get(self, request): print('In view') export_report_to_s3.delay() return HttpResponse('Success')
启动Celery Worker的命令
celery -A my_project worker -l INFO
现象
每次访问视图URL都会收到Success响应,SQS的飞行请求数增加,但Celery Worker无任务执行的输出。
排查与解决方法
1. 强制指定Worker监听的队列
启动Worker时显式指定目标队列,避免默认监听范围不匹配的问题:
celery -A my_project worker -l INFO -Q tk-test-queue
2. 检查AWS权限配置
确保Worker使用的AWS账号拥有以下SQS相关权限:
sqs:ReceiveMessagesqs:DeleteMessagesqs:GetQueueAttributessqs:ChangeMessageVisibility
权限不足会导致Worker能感知任务,但无法正常处理,最终任务卡在飞行状态。
3. 调整可见性超时参数
当前visibility-timeout设置为30分钟,远超任务实际执行时长,可能导致任务重复被拾取但无法完成。先缩短参数测试:
CELERY_BROKER_TRANSPORT_OPTIONS = { 'region': 'ap-south-1', 'visibility-timeout': 60 * 5, # 改为5分钟 'polling_interval': 2 # 适当增加轮询间隔,减少无效请求 }
4. 开启DEBUG日志排查细节
将日志级别调至DEBUG,查看任务接收后的反序列化、执行全流程细节:
celery -A my_project worker -l DEBUG -Q tk-test-queue
DEBUG日志会暴露任务执行环节的潜在问题,比如序列化失败、任务模块未加载等。
5. 确认任务自动发现生效
确保my_app已加入INSTALLED_APPS,也可以在celery.py中手动指定任务模块:
app.autodiscover_tasks(['my_app'])
内容的提问来源于stack exchange,提问作者Hrushikesh Vaidya
相关产品推荐
相关产品推荐

