Получение среднего значения нескольких оценок из разных экземпляров модели (Django)

Я работаю над веб-приложением, которое позволяет менеджеру проекта оценивать поставщика после завершения задачи/работы. Вот содержимое models.py:

class Rating(models.Model):
    RATE_CHOICES = [
        (1, 'Below Expectation greater than 0.02'),
        (2, 'Meet Expectaion 0.02'),
        (3, 'Exceed Expectaions less than 0.02'),
    ]
    
    reviewer = models.ForeignKey(CustomUser, related_name="evaluator", 
    on_delete=models.CASCADE, null=True, blank=True)
    reviewee = models.ForeignKey(Vendor, null=True, blank=True, 
     related_name="evaluated_vendor", on_delete=models.CASCADE)
    job = models.ForeignKey(Job, on_delete=models.CASCADE, null=True, blank=True, 
    related_name='jobrate')

    date = models.DateTimeField(auto_now_add=True)
    text = models.TextField(max_length=200, blank=True)
    rate = models.PositiveSmallIntegerField(choices=RATE_CHOICES)

class Job(models.Model):
    title = models.CharField(null=True, blank=True, max_length=100)
    project_manager = models.ForeignKey(CustomUser, on_delete = models.CASCADE, 
    related_name="assigned_by")
    startDate = models.DateField(blank=True, null=True)
    deadlineDate = models.DateField(blank=True, null=True)
    status = models.CharField(choices=STATUS, default='In Preparation', max_length=100)
    evaluated = models.BooleanField(default=False)
    #Related Fields
    purchaseOrder = models.ForeignKey(PurchaseOrder, blank=True, null=True, 
    on_delete=models.CASCADE)
    project = models.ForeignKey(Project, blank=True, null=True, 
    on_delete=models.CASCADE, related_name="Main_Project")
    assigned_to = models.ForeignKey(Vendor, blank=True, null=True, 
    on_delete=models.CASCADE, related_name="Job_owner")

class Vendor(models.Model):

    #Basic Fields.
    vendorName = models.CharField(null=True, blank=True, max_length=200)
    addressLine1 = models.CharField(null=True, blank=True, max_length=200)
    country = models.CharField(blank=True, choices=COUNTRY_CHOICES, max_length=100)
    postalCode = models.CharField(null=True, blank=True, max_length=10)
    phoneNumber = models.CharField(null=True, blank=True, max_length=100)
    emailAddress = models.CharField(null=True, blank=True, max_length=100)
    taxNumber = models.CharField(null=True, blank=True, max_length=100)
    mother_language = models.CharField(blank=True, choices=LANGUAGE_CHOICES, 
    max_length=300)

Вот мой view.py:

@login_required
def vendors(request):
    context = {}
    vendors = Vendor.objects.all()
    context['vendors'] = vendors
    

    if request.method == 'GET':
        form = VendorForm()
        context['form'] = form
        return render(request, 'projects/vendors.html', context)

    if request.method == 'POST':
        form = VendorForm(request.POST, request.FILES)

        if form.is_valid():
            form.save()

            messages.success(request, 'New Vendor Added')
            return redirect('vendors')
        else:
            messages.error(request, 'Problem processing your request')
            return redirect('vendors')


    return render(request, 'projects/vendors.html', context)

Затем в моем HTML я хочу отобразить среднюю оценку нескольких работ, выполненных данным поставщиком, в колонке Average rate. Например, если поставщик выполнил 2 задания и получил оценки 1 и 2 соответственно. Средняя оценка для этого продавца будет равна 1,5. Я хочу, чтобы в таблице отображалась эта средняя ставка.

Вот мои текущие настройки в моем HTML:

 <table class="table table-striped table-sm">
      <thead>
        <tr>
          <th scope="col">Vendor Name</th>
          <th scope="col">Mother Tongue</th>
          <th scope="col"> Average Rating</th>
          <th scope="col">Email Address</th>
          <th scope="col">Phone Number</th>
          <th scope="col">Address Line</th>
          <th scope="col">Country</th>
          
        </tr>
      </thead>
      <tbody>
        
      {% for vendor in vendors %}
      <tr>
        <td>{{vendor.vendorName}}</td>
        <td>{{vendor.mother_language}}</td>
        <td>{{vendor.averagerating | stringformat:".2f"}}</td>
        <td>{{vendor.emailAddress}}</td>
        <td>{{vendor.phoneNumber}}</td>
        <td>{{vendor.addressLine1}}</td>
        <td>{{vendor.country}}</td>
       
      </tr>
        {% endfor %}

      </tbody>
    </table>

Вопрос в том, как я могу получить средний рейтинг данного продавца по всем работам, которые он/она выполнил и отобразить его в моей таблице списка продавцов. Обратите внимание, что колонка среднего рейтинга в настоящее время не отображается, она пуста. Ваш ответ будет оценен по достоинству. Заранее спасибо.

Обозначьте vendors в вашем представлении средним значением связанных объектов рейтинга.

vendors = Vendor.objects.all().annotate(
    averagerating=Avg("evaluated_vendor__rate"),
)

Смотрите этот раздел документации для подробностей о том, как это работает.

Относится к посту AKX: Вы также можете попробовать получить агрегацию из модели Rating следующим образом:

vendor_ranking = Rating.objects.filter(reviewee=vendor).aggregate(Avg("rate"))
Вернуться на верх