Celery绑定类方法为任务触发AttributeError属性缺失问题求解
错误根因分析
- 你将Celery任务定义为类的实例方法属于错误用法:
@shared_task(bind=True)绑定的是Celery任务自身的实例,当你用该装饰器装饰类方法时,方法第一个参数接收到的是Celery任务对象,不是你自定义的myClass类的实例,这直接导致两个报错:- 你在方法里访问
self.location的时候,这里的self是Celery的download_all任务对象,自然没有location属性 - celery-progress的progress_recorder需要绑定Celery任务实例来调用
update_state,但你把myClass的实例传进去了,自然没有该方法
- 你在方法里访问
myClass的__init__方法里直接调用download_all逻辑错误,你要做异步任务的话不应该在实例初始化时同步执行该方法- views层的调用逻辑完全混乱:你既在实例化myClass的时候直接调用了download_all,又尝试对实例调用delay,还重复调用download_all取task_id,完全不符合Celery的调用规范
修复方案
1. 调整functions.py逻辑
将download_all从myClass中剥离为独立的Celery任务,避免实例指向混乱:
import os import shutil from celery import shared_task from celery_progress.backend import ProgressRecorder class myClass(): def __init__(self, n_user, n_password, n_url, n_port, db_password, username): self.location = zt_dosya_url # 确保该变量可正常获取,建议存到Django settings中统一调用 self.static_fields = {} self.username = username self.n_user = n_user self.n_password = n_password self.n_url = n_url self.n_port = n_port self.db_password = db_password def send(self): # 保留你原有的send逻辑 pass # 独立定义Celery异步任务 @shared_task(bind=True) def download_all_task(self, location, n_user, n_password, n_url, n_port, db_password, username): progress_recorder = ProgressRecorder(self) if not os.path.exists(location): os.mkdir(location) else: shutil.rmtree(location, ignore_errors=True) os.mkdir(location) # 保留你原有获取scans的业务逻辑 scans = [] len_scans = len(scans) for i, s in enumerate(scans): scanner.scan_name = s['name'] # 你的原有业务逻辑 progress_recorder.set_progress(i + 1, len_scans, f'On iteration {i}') # 下载完成后执行send逻辑 my_class_instance = myClass(n_user, n_password, n_url, n_port, db_password, username) my_class_instance.send()
2. 修正views.py调用逻辑
直接调用异步任务获取task_id,不要多余的myClass实例化操作:
def setup_wizard(request): # 保留你原有获取setup对象的逻辑 task = download_all_task.delay( zt_dosya_url, # 传入location参数 setup.n_username, setup.n_password, setup.n_url, setup.ns_port, setup.db_password, request.user.username ) task_id = task.task_id context = { 'task_id': task_id } # 保留你原有返回逻辑
内容的提问来源于stack exchange,提问作者edche
相关产品推荐
相关产品推荐

