7. With a few exceptions…
constraint names on 64-bit platforms
8. With a few exceptions…
constraint names on 64-bit platforms
transactions in tests
9. With a few exceptions…
constraint names on 64-bit platforms
transactions in tests
SetRemoteAddrFromForwardedFor middleware
10. With a few exceptions…
constraint names on 64-bit platforms
transactions in tests
SetRemoteAddrFromForwardedFor middleware
saving of model formsets
11. With a few exceptions…
constraint names on 64-bit platforms
transactions in tests
SetRemoteAddrFromForwardedFor middleware
saving of model formsets
names of uploaded files
12. Also…
changed admin autodiscovery
if your urlconf contains:
(r'^admin/(.*)', admin.site.root),
change it to be:
(r'^admin/', include(admin.site.urls)),
21. What are aggregates?
• aggregate()
summary for entire query
• annotate()
summary per row returned
22. Aggregate Examples
Person Purchases
first_name CharField thing CharField
last_name CharField price DecimalField
age IntField person FK
What is the average age for all people?
>>> Person.objects.aggregate(Avg(‘age’))
{‘age__avg’: 23.65}
23. Aggregate Examples
Person Purchases
first_name CharField thing CharField
last_name CharField price DecimalField
age IntField person FK
What is the average age for all people?
>>> Person.objects.aggregate(Avg(‘age’), Min(‘age’),
Max(‘age’))
{‘age__avg’: 23.65, ‘age__min’: 14, ‘age__max’:87}
24. Aggregate Examples
Person Purchases
first_name CharField thing CharField
last_name CharField price DecimalField
age IntField person FK
What is the average age for all people?
>>> Person.objects.aggregate(Avg(‘age’), Min(‘age’),
Max(‘age’))
{‘age__avg’: 23.65, ‘age__min’: 14, ‘age__max’:87}
No Chaining!
25. Aggregation functions
• Avg(field): average of field
• Min(field): min of field
• Max(field): max of field
• Sum(field): sum of all values in the field
• Count(field, distinct): num of related objects via field
• StdDev(field, sample)
• Variance(field, sample)
26. Annotation
Person Purchases
first_name CharField thing CharField
last_name CharField price DecimalField
age IntField person FK
People ordered by number of purchases made
q = Person.objects.annotate(Count(‘purchases’)).order_by(
‘-purchases__count’)
>>> q[0]
<Person: Material Girl>
>>> q[0].purchases__count
4592810191
27. Annotation
Person Purchases
first_name CharField thing CharField
last_name CharField price DecimalField
age IntField person FK
People ordered by number of purchases made
q = Person.objects.annotate(num_purchases=Count(‘purchases’))
.order_by(‘-num_purchases’)
>>> q[0]
<Person: Material Girl>
>>> q[0].num_purchases
4592810191
28. Annotation
Person Purchases
first_name CharField thing CharField
last_name CharField price DecimalField
age IntField person FK
Which people have <=10 purchases?
q = Person.objects.annotate(
num_purchases=Count(‘purchases’)).filter(num_purchases__lte=10)
29. Annotation
Person Purchases
first_name CharField thing CharField
last_name CharField price DecimalField
age IntField person FK
Annotations work across JOINs:
What is the average purchase price for
purchases made by each person?
Person.objects.annotate(min_price=Min(‘purchases__price’))
33. F( ) Expressions
class Stock(models.Model):
symbol = models.CharField()
class TradingDay(models.Model):
stock = models.ForeignKey(Stock, related_name="days")
opening = models.DecimalField()
closing = models.DecimalField()
high = models.DecimalField()
low = models.DecimalField()
34. F( ) Expressions
class Stock(models.Model):
symbol = models.CharField()
class TradingDay(models.Model):
stock = models.ForeignKey(Stock, related_name="days")
opening = models.DecimalField()
closing = models.DecimalField()
high = models.DecimalField()
low = models.DecimalField()
from django.db.models import F
# Closed at least 50% up from open
TradingDay.objects.filter(closing__gte=F('opening') * 1.5)
# All downhill
TradingDay.objects.filter(opening=F('high'))
# Works across JOINs
# Stocks that have days with <10pt loss in value
Stock.objects.filter(days__closing__gte=F('days__opening')-10.0)
35. F( ) Expressions
Atomic DB Increment Operations!
class MyModel():
...
counter = models.IntegerField()
MyModel.objects.filter(id=someid).update(counter=F('counter')+1)
37. Unmanaged Models
• Useful for tables or DB views which
aren’t under Django’s control
• Work like regular models
• No table creation during syncdb,
tests, etc.
39. Proxy Models
I already have a model, and
want to change its python
behavior without changing
the underlying table
structure.
40. Proxy Models
class MyProxy(MyModel):
# no new fields!
# but you can define new managers
objects = SupaDupaProxyManager()
proxy_specific_manager = PonyManager()
class Meta:
proxy = True
ordering = ['not_the_original_ordering_field',]
def my_proxy_method(self):
# ... do something