Kaydet (Commit) dbffffa7 authored tarafından Jannis Leidel's avatar Jannis Leidel

Fixed #5535 -- Allow using an explicit foreign key in get() calls. Thanks, Michal Petrucha.

git-svn-id: http://code.djangoproject.com/svn/django/trunk@16473 bcc190cf-cafb-0310-a4f2-bffc1f526a37
üst f54135fa
...@@ -1068,8 +1068,9 @@ class Query(object): ...@@ -1068,8 +1068,9 @@ class Query(object):
try: try:
field, target, opts, join_list, last, extra_filters = self.setup_joins( field, target, opts, join_list, last, extra_filters = self.setup_joins(
parts, opts, alias, True, allow_many, can_reuse=can_reuse, parts, opts, alias, True, allow_many, allow_explicit_fk=True,
negate=negate, process_extras=process_extras) can_reuse=can_reuse, negate=negate,
process_extras=process_extras)
except MultiJoin, e: except MultiJoin, e:
self.split_exclude(filter_expr, LOOKUP_SEP.join(parts[:e.level]), self.split_exclude(filter_expr, LOOKUP_SEP.join(parts[:e.level]),
can_reuse) can_reuse)
......
...@@ -365,6 +365,16 @@ translates (roughly) into the following SQL:: ...@@ -365,6 +365,16 @@ translates (roughly) into the following SQL::
.. _`Keyword Arguments`: http://docs.python.org/tutorial/controlflow.html#keyword-arguments .. _`Keyword Arguments`: http://docs.python.org/tutorial/controlflow.html#keyword-arguments
.. versionchanged:: 1.4
The field specified in a lookup has to be the name of a model field.
There's one exception though, in case of a
:class:`~django.db.models.fields.ForeignKey` you can specify the field
name suffixed with ``_id``. In this case, the value parameter is expected
to contain the raw value of the foreign model's primary key. For example::
>>> Entry.objects.filter(blog_id__exact=4)
If you pass an invalid keyword argument, a lookup function will raise If you pass an invalid keyword argument, a lookup function will raise
``TypeError``. ``TypeError``.
......
...@@ -2,7 +2,7 @@ from copy import deepcopy ...@@ -2,7 +2,7 @@ from copy import deepcopy
from datetime import datetime from datetime import datetime
from django.test import TestCase from django.test import TestCase
from django.core.exceptions import FieldError from django.core.exceptions import FieldError, MultipleObjectsReturned
from models import Article, Reporter from models import Article, Reporter
...@@ -229,10 +229,6 @@ class ManyToOneTests(TestCase): ...@@ -229,10 +229,6 @@ class ManyToOneTests(TestCase):
"<Article: John's second story>", "<Article: John's second story>",
"<Article: This is a test>", "<Article: This is a test>",
]) ])
# You need two underscores between "reporter" and "id" -- not one.
self.assertRaises(FieldError, Article.objects.filter, reporter_id__exact=self.r.id)
# You need to specify a comparison clause
self.assertRaises(FieldError, Article.objects.filter, reporter_id=self.r.id)
def test_reverse_selects(self): def test_reverse_selects(self):
a3 = Article.objects.create(id=None, headline="Third article", a3 = Article.objects.create(id=None, headline="Third article",
...@@ -372,3 +368,34 @@ class ManyToOneTests(TestCase): ...@@ -372,3 +368,34 @@ class ManyToOneTests(TestCase):
# recursive don't cause recursion depth problems under deepcopy. # recursive don't cause recursion depth problems under deepcopy.
self.r.cached_query = Article.objects.filter(reporter=self.r) self.r.cached_query = Article.objects.filter(reporter=self.r)
self.assertEqual(repr(deepcopy(self.r)), "<Reporter: John Smith>") self.assertEqual(repr(deepcopy(self.r)), "<Reporter: John Smith>")
def test_explicit_fk(self):
# Create a new Article with get_or_create using an explicit value
# for a ForeignKey.
a2, created = Article.objects.get_or_create(id=None,
headline="John's second test",
pub_date=datetime(2011, 5, 7),
reporter_id=self.r.id)
self.assertTrue(created)
self.assertEqual(a2.reporter.id, self.r.id)
# You can specify filters containing the explicit FK value.
self.assertQuerysetEqual(
Article.objects.filter(reporter_id__exact=self.r.id),
[
"<Article: John's second test>",
"<Article: This is a test>",
])
# Create an Article by Paul for the same date.
a3 = Article.objects.create(id=None, headline="Paul's commentary",
pub_date=datetime(2011, 5, 7),
reporter_id=self.r2.id)
self.assertEqual(a3.reporter.id, self.r2.id)
# Get should respect explicit foreign keys as well.
self.assertRaises(MultipleObjectsReturned,
Article.objects.get, reporter_id=self.r.id)
self.assertEqual(repr(a3),
repr(Article.objects.get(reporter_id=self.r2.id,
pub_date=datetime(2011, 5, 7))))
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment