views:

99

answers:

1

I have these models in Django:

class Customer(models.Model):
    def __unicode__(self):
        return self.name
    name = models.CharField(max_length=200)

class Sale(models.Model):
    def __unicode__(self):
        return "Sale %s (%i)" % (self.type, self.id)
    customer = models.ForeignKey(Customer)
    total = models.DecimalField(max_digits=15, decimal_places=3)
    notes = models.TextField(blank=True, null=True)

class Unitary_Sale(models.Model):
    book = models.ForeignKey(Book)
    quantity = models.IntegerField()
    unit_price = models.DecimalField(max_digits=15, decimal_places=3)
    sale = models.ForeignKey(Sale)

How can I filter to get all books that customer sale?

I tried:

units=Unitary_Sale.objects.all()
>>> units=Unitary_Sale.objects.all()
>>> for unit in units:
...    print unit.sale.customer
...    print unit.book,unit.sale.total
...
Sok nara
Khmer Empire (H001) 38.4
Sok nara
killing field (H001) 16

San ta
khmer krom (H001) 20
San ta
Khmer Empire (H001) 20
>>>

what I want:

  sok nora:56.4 (38.4+18)
  san ta:40 (20+20)

Or to dictionary:

{sok nora:156.4, san ta:40}

>>> store_resulte = {}
>>> for unit in units:
...    store_resulte[unit.sale.customer] = unit.sale.total
...
>>> print store_resulte

    {<Customer: Sok nara>: Decimal("16"), <Customer: san ta>: Decimal("20")}

It should be:

{<Customer: Sok nara>: Decimal("56.4"), <Customer: san ta>: Decimal("40")}
+1  A: 

Have a look at aggregation documentation.

I believe this should do the trick (only with version 1.1 or dev.):

Customer.objects.annotate(total=Sum('sale__total'))

EDIT: You can also define a custom method for the class:

class Customer(models.Model):
    def __unicode__(self):
        return self.name
    name = models.CharField(max_length=200)

    def total_sale(self):
        total = 0
        for s in self.sale_set:
           total += s.total
        return total
jbochi
AttributeError: 'Manager' object has no attribute 'annotate'
python
Which Django version are you using? try to replace `annotate` by `aggregate`.
jbochi
It's adapt my question?so what I should applied this to my quiz? :)
python
look at my posting.I changed annotate to aggregate it the same error.for your customer method How can I use it? thanks
python
If you define a method in the model Class, it will be available for every Customer instance. It's something like `Customer.objects.get(name='Sok nara').total_sale()`
jbochi
when I Customer.objects.get(name='Sok nara').total_sale<bound method Customer.total_sale of <Customer: Mesa>> Not any results???
python
When I Customer.objects.get(name='Sok nara').total_sale()Traceback (most recent call last): File "<console>", line 1, in <module> File "..../models.py", line 118, in total_sale for s in self.sale_set:TypeError: 'RelatedManager' object is not iterable
python