summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTim Graham <timograham@gmail.com>2015-08-03 17:05:18 -0400
committerTim Graham <timograham@gmail.com>2015-08-05 08:15:44 -0400
commitce0f2a4a4f192caf46cc9edd843c87862a668161 (patch)
tree394dba8551421384a16928daec08c9682c98cda2
parent6f6043fd26a83bd0625ce34e1f64a1663fec26db (diff)
[1.8.x] Fixed #25213 -- Discouraged use of QuerySet.extra()
Thanks Anssi Kääriäinen for the draft text and Simon Charette for review. Backport of e8cd65f8297928d3fa7ad3d338953a4423028713 from master
-rw-r--r--docs/ref/models/querysets.txt28
-rw-r--r--docs/topics/db/optimization.txt10
2 files changed, 33 insertions, 5 deletions
diff --git a/docs/ref/models/querysets.txt b/docs/ref/models/querysets.txt
index 8170a86e8c..c794bb27ef 100644
--- a/docs/ref/models/querysets.txt
+++ b/docs/ref/models/querysets.txt
@@ -1136,6 +1136,34 @@ Sometimes, the Django query syntax by itself can't easily express a complex
``QuerySet`` modifier — a hook for injecting specific clauses into the SQL
generated by a ``QuerySet``.
+.. admonition:: Use this method as a last resort
+
+ This is an old API that we aim to deprecate at some point in the future.
+ Use it only if you cannot express your query using other queryset methods.
+ If you do need to use it, please `file a ticket
+ <https://code.djangoproject.com/newticket>`_ using the `QuerySet.extra
+ keyword <https://code.djangoproject.com/query?status=assigned&status=new&keywords=~QuerySet.extra>`_
+ with your use case (please check the list of existing tickets first) so
+ that we can enhance the QuerySet API to allow removing ``extra()``. We are
+ no longer improving or fixing bugs for this method.
+
+ For example, this use of ``extra()``::
+
+ >>> qs.extra(
+ ... select={'val': "select col from sometable where othercol = %s"},
+ ... select_params=(someparam,),
+ ... )
+
+ is equivalent to::
+
+ >>> qs.annotate(val=RawSQL("select col from sometable where othercol = %s", (someparam,)))
+
+ The main benefit of using :class:`~django.db.models.expressions.RawSQL` is
+ that you can set ``output_field`` if needed. The main downside is that if
+ you refer to some table alias of the queryset in the raw SQL, then it is
+ possible that Django might change that alias (for example, when the
+ queryset is used as a subquery in yet another query).
+
.. warning::
You should be very careful whenever you use ``extra()``. Every time you use
diff --git a/docs/topics/db/optimization.txt b/docs/topics/db/optimization.txt
index 8847663b1b..52238bd714 100644
--- a/docs/topics/db/optimization.txt
+++ b/docs/topics/db/optimization.txt
@@ -130,12 +130,12 @@ For instance:
If these aren't enough to generate the SQL you need:
-Use ``QuerySet.extra()``
-------------------------
+Use ``RawSQL``
+--------------
-A less portable but more powerful method is
-:meth:`~django.db.models.query.QuerySet.extra()`, which allows some SQL to be
-explicitly added to the query. If that still isn't powerful enough:
+A less portable but more powerful method is the
+:class:`~django.db.models.expressions.RawSQL` expression, which allows some SQL
+to be explicitly added to the query. If that still isn't powerful enough:
Use raw SQL
-----------