我正在尝试创建一个后台任务,使用Django芹菜和Redis作为代理。此任务是在模型后期保存时从模型发送的。但问题是,同一个任务被执行了1000次(其他调试或添加任务运行良好(。我已经尝试过这种方法,但这并没有解决问题。请找到以下代码供您参考并帮助解决。提前谢谢。
型号.py
from django.db.models.signals import post_save
from django.dispatch import receiver
from student.tasks import create_student_subject_tryout_result, add
@receiver(post_save, sender=TryoutSubmission,
dispatch_uid='create_student_subject_tryout_result')
def result_calculation(sender, instance, **kwargs):
if instance.status == 'C':
print('Calculating result')
create_student_subject_tryout_result.delay(instance.student.id,
instance.tryout.id)
芹菜.py
import os
from celery import Celery
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'eec.settings')
app = Celery('eec')
app.config_from_object('django.conf:settings', namespace='CELERY')
app.conf.broker_transport_options = {'visibility_timeout': 3600} .
app.autodiscover_tasks()
@app.task(bind=True)
def debug_task(self):
print(f'Request: {self.request!r}')
任务.py
from celery import shared_task
import tryout.models
@shared_task(bind=True)
def create_student_subject_tryout_result(self, student_id, tryout_id):
tryout_submission=tryout.models.TryoutSubmission.objects.get(
student_id=student_id, tryout_id=tryout_id
)
tryout_questions = tryout_submission.tryout.tryoutquestion_set.all().count()
answered_qs = tryout_submission.tryout.tryoutanswersubmission_set.filter(
is_answered=True).count()
correct_ans = tryout_submission.tryout.tryoutanswersubmission_set.filter(
is_correct=True).count()
tryout_submission.total_questions = tryout_questions
tryout_submission.answered_questions = answered_qs
tryout_submission.correct_answers = correct_ans
tryout_submission.total_time = tryout_submission.end_time - tryout_submission.start_time
tryout_submission.save()
return "Result created"
设置.py
CELERY_RESULT_BACKEND = 'django-db'
CELERY_CACHE_BACKEND = 'django-cache'
CELERY_BROKER_URL = 'redis://localhost:6379'
CELERY_ACCEPT_CONTENT = ['application/json']
CELERY_TASK_SERIALIZER = 'json'
CELERY_RESULT_SERIALIZER = 'json'
CELERY_TIMEZONE = 'Asia/Kolkata'
CELERY_BEAT_SCHEDULER = 'django_celery_beat.schedulers:DatabaseScheduler'
好吧,如果你看看你的接收器,你正在听你的模型上的post_save
。
CCD_ 2信号还提供CCD_。不检查instance.status == 'C'
,而是检查已创建的:
from django.db.models.signals import post_save
from django.dispatch import receiver
from student.tasks import create_student_subject_tryout_result, add
@receiver(post_save, sender=TryoutSubmission,
dispatch_uid='create_student_subject_tryout_result')
def result_calculation(sender, instance, raw, created, **kwargs):
if created:
print('Calculating result')
create_student_subject_tryout_result.delay(
instance.student.id,
instance.tryout.id
)