diff options
| author | Marc Tamlyn <marc.tamlyn@gmail.com> | 2013-10-15 13:15:02 +0100 |
|---|---|---|
| committer | Marc Tamlyn <marc.tamlyn@gmail.com> | 2013-10-15 15:59:36 +0100 |
| commit | 349c12d3f5c015c2f8b36917da21230c2ac1acb4 (patch) | |
| tree | d1a8dfb839ecd3d9c65f55fcb93a27a7ba773b25 /docs | |
| parent | dd1ab8982be0ab8bd648b57c0bbc6a100a429695 (diff) | |
Fixed #16855 -- select_related() chains as expected.
select_related('foo').select_related('bar') is now equivalent to
select_related('foo', 'bar').
Also reworded docs to recommend select_related(*fields) over select_related()
Diffstat (limited to 'docs')
| -rw-r--r-- | docs/ref/models/querysets.txt | 74 | ||||
| -rw-r--r-- | docs/releases/1.7.txt | 6 |
2 files changed, 32 insertions, 48 deletions
diff --git a/docs/ref/models/querysets.txt b/docs/ref/models/querysets.txt index e2b6efc93a..170df975bd 100644 --- a/docs/ref/models/querysets.txt +++ b/docs/ref/models/querysets.txt @@ -688,13 +688,12 @@ manager or a ``QuerySet`` and do further filtering on the result. After calling select_related ~~~~~~~~~~~~~~ -.. method:: select_related() +.. method:: select_related(*fields) -Returns a ``QuerySet`` that will automatically "follow" foreign-key -relationships, selecting that additional related-object data when it executes -its query. This is a performance booster which results in (sometimes much) -larger queries but means later use of foreign-key relationships won't require -database queries. +Returns a ``QuerySet`` that will "follow" foreign-key relationships, selecting +additional related-object data when it executes its query. This is a +performance booster which results in a single more complex query but means +later use of foreign-key relationships won't require database queries. The following examples illustrate the difference between plain lookups and ``select_related()`` lookups. Here's standard lookup:: @@ -708,13 +707,13 @@ The following examples illustrate the difference between plain lookups and And here's ``select_related`` lookup:: # Hits the database. - e = Entry.objects.select_related().get(id=5) + e = Entry.objects.select_related('blog').get(id=5) # Doesn't hit the database, because e.blog has been prepopulated # in the previous query. b = e.blog -``select_related()`` follows foreign keys as far as possible. If you have the +You can follow foreign keys in a similar way to querying them. If you have the following models:: from django.db import models @@ -731,10 +730,11 @@ following models:: # ... author = models.ForeignKey(Person) -...then a call to ``Book.objects.select_related().get(id=4)`` will cache the -related ``Person`` *and* the related ``City``:: +...then a call to ``Book.objects.select_related('person', +'person__city').get(id=4)`` will cache the related ``Person`` *and* the related +``City``:: - b = Book.objects.select_related().get(id=4) + b = Book.objects.select_related('person__city').get(id=4) p = b.author # Doesn't hit the database. c = p.hometown # Doesn't hit the database. @@ -742,45 +742,9 @@ related ``Person`` *and* the related ``City``:: p = b.author # Hits the database. c = p.hometown # Hits the database. -Note that, by default, ``select_related()`` does not follow foreign keys that -have ``null=True``. - -Usually, using ``select_related()`` can vastly improve performance because your -app can avoid many database calls. However, there are times you are only -interested in specific related models, or have deeply nested sets of -relationships, and in these cases ``select_related()`` can be optimized by -explicitly passing the related field names you are interested in. Only -the specified relations will be followed. - -You can even do this for models that are more than one relation away by -separating the field names with double underscores, just as for filters. For -example, if you have this model:: - - class Room(models.Model): - # ... - building = models.ForeignKey(...) - - class Group(models.Model): - # ... - teacher = models.ForeignKey(...) - room = models.ForeignKey(Room) - subject = models.ForeignKey(...) - -...and you only needed to work with the ``room`` and ``subject`` attributes, -you could write this:: - - g = Group.objects.select_related('room', 'subject') - -This is also valid:: - - g = Group.objects.select_related('room__building', 'subject') - -...and would also pull in the ``building`` relation. - You can refer to any :class:`~django.db.models.ForeignKey` or :class:`~django.db.models.OneToOneField` relation in the list of fields -passed to ``select_related()``. This includes foreign keys that have -``null=True`` (which are omitted in a no-parameter ``select_related()`` call). +passed to ``select_related()``. You can also refer to the reverse direction of a :class:`~django.db.models.OneToOneField` in the list of fields passed to @@ -789,6 +753,13 @@ You can also refer to the reverse direction of a is defined. Instead of specifying the field name, use the :attr:`related_name <django.db.models.ForeignKey.related_name>` for the field on the related object. +There may be some situations where you wish to call ``select_related()`` with a +lot of related objects, or where you don't know all of the relations. In these +cases it is possible to call ``select_related()`` with no arguments. This will +follow all non-null foreign keys it can find - nullable foreign keys must be +specified. This is not recommended in most cases as it is likely to make the +underlying query more complex, and return more data, than is actually needed. + .. versionadded:: 1.6 If you need to clear the list of related fields added by past calls of @@ -796,6 +767,13 @@ If you need to clear the list of related fields added by past calls of >>> without_relations = queryset.select_related(None) +.. versionchanged:: 1.7 + +Chaining ``select_related`` calls now works in a similar way to other methods - +that is that ``select_related('foo', 'bar')`` is equivalent to +``select_related('foo').select_related('bar')``. Previously the latter would +have been equivalent to ``select_related('bar')``. + prefetch_related ~~~~~~~~~~~~~~~~ diff --git a/docs/releases/1.7.txt b/docs/releases/1.7.txt index a3fdc0e9f3..aa613c4538 100644 --- a/docs/releases/1.7.txt +++ b/docs/releases/1.7.txt @@ -533,6 +533,12 @@ Miscellaneous you relied on the default field ordering while having fields defined on both the current class *and* on a parent ``Form``. +* :meth:`~django.db.models.query.QuerySet.select_related` now chains in the + same way as other similar calls like ``prefetch_related``. That is, + ``select_related('foo', 'bar')`` is equivalent to + ``select_related('foo').select_related('bar')``. Previously the latter would + have been equivalent to ``select_related('bar')``. + Features deprecated in 1.7 ========================== |
