How can I access the count of a field in Django model?

Question:

I want to display the total revenue which equals total price, and total price is a field in the appointments model
I want the count of that specific field so I can display it in the HTML.

class Appointment(models.Model):

    # Invoicing Section
    service_name = models.CharField(max_length=120, default='', blank=True, null=True)
    total_price = models.CharField(max_length=100,default='', blank=True, null=True)
    upfront_payment = models.CharField(max_length=100,default='', blank=True, null=True)
    grand_total = models.CharField(max_length=100,default='', blank=True, null=True)
    invoice_date = models.DateField(auto_now_add=True, blank=True, null=True)
    invoice_type_choice = (
            ('EVCPLUS', 'EVCPLUS'),
            ('SH.SO', 'SH.SO'),
            ('USD', 'USD'),
        )
    invoice_type = models.CharField(max_length=50, default='', blank=True, null=True, choices=invoice_type_choice)
    payment_status = models.CharField(max_length=10, choices=(('Pending', 'Pending'), 
        ('Completed', 'Completed'), ('Canceled', 'Canceled')), default='Pending')


    def __str__(self):
        return self.patient.patient_name

i tried doing this :

 revenue = Appointment.objects.filter(total_price = Appointment.total_price).count()

            return render(request, 'index.html', {
                'current_user': current_user,
                'sayfa': 'dashboard',
                'yearly_patients': yearly_patients,
                'monthly_appointments': monthly_appointments,
                'yearly_patients_graph': yearly_patients_dict,
                'monthly_appointments_graph':monthly_appointments_dict,
                'donutDataGraph': donutData,
                'appointments': appointments,
                'doctors': doctors,
                'revenue': revenue,
                'search_patient_form': form,
                'search_patient_form': search_patient_form
                })

but it returned 0 which is not true.

Asked By: Smokar

||

Answers:

So, there are a few issues in your approache.

First, count() does not calculate a sum, but counts the number of entries. This is however a good start as it aggregates the records in your database.

Second, .filter(total_price = Appointment.total_price) doesn’t make any sense. With this statement, you compare the db value with a field type. Also, you do not want to filter your records if you want to aggregate all rows.

Third, to make sum, you will need to have a numeric data type. However, total_price is a textual data type (CharField). You will need to use a numeric field (such as IntegerField for an integer amount, or DecimalField for a decimal amount with fixed number of decimals):

total_price = models.DecimalField(max_digits=9, decimal_places=2, blank=True, null=True)

Note that changing the data type will require you to make a migration and converting text to numeric data type will probably fail. However handling this kind of migration is out of the scope of this question.

Now that you have a numeric data type, you can do numeric aggregations:

from django.db.models import Sum
revenue = Appointment.objects.aggregate(revenue=Sum('total_price'))['revenue']
Answered By: Antoine Pinsard
Categories: questions Tags: , ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.