Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Django 1.6 A.objects.all().order_by(['field']) what will django do if the 'field' is the default order in a model?

Tags:

django

Say I have a Question model:

class Question(models.Model):
    class Meta:
        ordering = ['title']
    user = models.ForeignKey(User) 
    title = models.CharField()

If you define ordering in Meta, is it just a default setting for you to type less words, so the performances of Question.objects.all().order_by(['title']) and Question.objects.all() will be the same?

like image 489
tcpiper Avatar asked Feb 10 '14 10:02

tcpiper


1 Answers

Yes, performance is the same. Specifying Meta.ordering acts exactly like appending order_by to each query.

You can watch SQL queries that Django generates by setting DEBUG level for logger django.db.backends.

Example models:

class ModelA(models.Model):
    dummy = models.TextField()


class ModelB(models.Model):
    dummy = models.TextField()

    class Meta:
        ordering = ['dummy']

SQL queries examples:

>>> import logging
>>> l = logging.getLogger('django.db.backends')
>>> l.setLevel(logging.DEBUG)
>>> l.addHandler(logging.StreamHandler())

>>> from sqlorder.models import ModelA, ModelB
>>> ModelA.objects.all()
(0.111) SELECT "sqlorder_modela"."id", "sqlorder_modela"."dummy" 
FROM "sqlorder_modela" LIMIT 21; args=()
[]

ModelA has no ordering by default, so ModelA.objects.all does not appends ORDER BY to query. You can append it manually.

>>> ModelA.objects.order_by('dummy')
(0.001) SELECT "sqlorder_modela"."id", "sqlorder_modela"."dummy" 
FROM "sqlorder_modela" 
ORDER BY "sqlorder_modela"."dummy" ASC LIMIT 21; args=()
[]

ModelB has default ordering. Query is the same as for ModelA with manual addition of order_by.

>>> ModelB.objects.all()
(0.001) SELECT "sqlorder_modelb"."id", "sqlorder_modelb"."dummy" 
FROM "sqlorder_modelb" 
ORDER BY "sqlorder_modelb"."dummy" ASC LIMIT 21; args=()
[]

Update: Default ordering does not adds any additional indices to database:

$ python manage.py sqlall sqlorder
BEGIN;
CREATE TABLE "sqlorder_modela" (
    "id" serial NOT NULL PRIMARY KEY,
    "dummy" text NOT NULL
)
;
CREATE TABLE "sqlorder_modelb" (
    "id" serial NOT NULL PRIMARY KEY,
    "dummy" text NOT NULL
)
;

COMMIT;
like image 116
Vladimir Lagunov Avatar answered Nov 02 '22 19:11

Vladimir Lagunov