Deprecated depth kwarg on select_related.

This is the start of a deprecation path for the depth kwarg on
select_related. Removing this will allow us to update select_related so
it chains properly and have an API similar to prefetch_related.

Thanks to Marc Tamlyn for spearheading and initial patch.

refs #16855
This commit is contained in:
Preston Holmes 2012-11-02 15:49:29 +00:00
parent 7b57a72d6d
commit 965cc0b1ff
4 changed files with 30 additions and 14 deletions

View File

@ -5,6 +5,7 @@ The main QuerySet implementation. This provides the public API for the ORM.
import copy import copy
import itertools import itertools
import sys import sys
import warnings
from django.core import exceptions from django.core import exceptions
from django.db import connections, router, transaction, IntegrityError from django.db import connections, router, transaction, IntegrityError
@ -698,6 +699,9 @@ class QuerySet(object):
If fields are specified, they must be ForeignKey fields and only those If fields are specified, they must be ForeignKey fields and only those
related objects are included in the selection. related objects are included in the selection.
""" """
if 'depth' in kwargs:
warnings.warn('The "depth" keyword argument has been deprecated.\n'
'Use related field names instead.', PendingDeprecationWarning)
depth = kwargs.pop('depth', 0) depth = kwargs.pop('depth', 0)
if kwargs: if kwargs:
raise TypeError('Unexpected keyword arguments to select_related: %s' raise TypeError('Unexpected keyword arguments to select_related: %s'

View File

@ -298,6 +298,9 @@ these changes.
* The ``daily_cleanup.py`` script will be removed. * The ``daily_cleanup.py`` script will be removed.
* The ``depth`` keyword argument will be removed from
:meth:`~django.db.models.query.QuerySet.select_related`.
2.0 2.0
--- ---

View File

@ -676,21 +676,12 @@ Note that, by default, ``select_related()`` does not follow foreign keys that
have ``null=True``. have ``null=True``.
Usually, using ``select_related()`` can vastly improve performance because your Usually, using ``select_related()`` can vastly improve performance because your
app can avoid many database calls. However, in situations with deeply nested app can avoid many database calls. However, there are times you are only
sets of relationships ``select_related()`` can sometimes end up following "too interested in specific related models, or have deeply nested sets of
many" relations, and can generate queries so large that they end up being slow. relationships, and in these cases ``select_related()`` can can be optimized by
explicitly passing the related field names you are interested in. Only
the specified relations will be followed.
In these situations, you can use the ``depth`` argument to ``select_related()``
to control how many "levels" of relations ``select_related()`` will actually
follow::
b = Book.objects.select_related(depth=1).get(id=4)
p = b.author # Doesn't hit the database.
c = p.hometown # Requires a database call.
Sometimes you only want to access specific models that are related to your root
model, not all of the related models. In these cases, you can pass the related
field names to ``select_related()`` and it will only follow those relations.
You can even do this for models that are more than one relation away by 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 separating the field names with double underscores, just as for filters. For
example, if you have this model:: example, if you have this model::
@ -730,6 +721,17 @@ You can also refer to the reverse direction of a
is defined. Instead of specifying the field name, use the :attr:`related_name 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. <django.db.models.ForeignKey.related_name>` for the field on the related object.
.. deprecated:: 1.5
The ``depth`` parameter to ``select_related()`` has been deprecated. You
should replace it with the use of the ``(*fields)`` listing specific
related fields instead as documented above.
A depth limit of relationships to follow can also be specified::
b = Book.objects.select_related(depth=1).get(id=4)
p = b.author # Doesn't hit the database.
c = p.hometown # Requires a database call.
A :class:`~django.db.models.OneToOneField` is not traversed in the reverse A :class:`~django.db.models.OneToOneField` is not traversed in the reverse
direction if you are performing a depth-based ``select_related()`` call. direction if you are performing a depth-based ``select_related()`` call.

View File

@ -638,3 +638,10 @@ The :djadmin:`cleanup` management command has been deprecated and replaced by
The undocumented ``daily_cleanup.py`` script has been deprecated. Use the The undocumented ``daily_cleanup.py`` script has been deprecated. Use the
:djadmin:`clearsessions` management command instead. :djadmin:`clearsessions` management command instead.
``depth`` keyword argument in ``select_related``
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The ``depth`` keyword argument in
:meth:`~django.db.models.query.QuerySet.select_related` has been deprecated.
You should use field names instead.