Fixed #31190 -- Fixed prefetch_related() crash for GenericForeignKey with custom ContentType foreign key.
Regression in dffa3e1992
.
This commit is contained in:
parent
b753e0e750
commit
0b013564ef
|
@ -583,11 +583,12 @@ def create_generic_related_manager(superclass, rel):
|
||||||
# We (possibly) need to convert object IDs to the type of the
|
# We (possibly) need to convert object IDs to the type of the
|
||||||
# instances' PK in order to match up instances:
|
# instances' PK in order to match up instances:
|
||||||
object_id_converter = instances[0]._meta.pk.to_python
|
object_id_converter = instances[0]._meta.pk.to_python
|
||||||
|
content_type_id_field_name = '%s_id' % self.content_type_field_name
|
||||||
return (
|
return (
|
||||||
queryset.filter(query),
|
queryset.filter(query),
|
||||||
lambda relobj: (
|
lambda relobj: (
|
||||||
object_id_converter(getattr(relobj, self.object_id_field_name)),
|
object_id_converter(getattr(relobj, self.object_id_field_name)),
|
||||||
relobj.content_type_id
|
getattr(relobj, content_type_id_field_name),
|
||||||
),
|
),
|
||||||
lambda obj: (obj.pk, self.get_content_type(obj).pk),
|
lambda obj: (obj.pk, self.get_content_type(obj).pk),
|
||||||
False,
|
False,
|
||||||
|
|
|
@ -35,3 +35,7 @@ Bugfixes
|
||||||
* Fixed a regression in Django 2.2.7 that caused
|
* Fixed a regression in Django 2.2.7 that caused
|
||||||
:meth:`~django.db.models.Model.get_FOO_display` to work incorrectly when
|
:meth:`~django.db.models.Model.get_FOO_display` to work incorrectly when
|
||||||
overriding inherited choices (:ticket:`31124`).
|
overriding inherited choices (:ticket:`31124`).
|
||||||
|
|
||||||
|
* Fixed a regression in Django 3.0 that caused a crash of
|
||||||
|
``QuerySet.prefetch_related()`` for ``GenericForeignKey`` with a custom
|
||||||
|
``ContentType`` foreign key (:ticket:`31190`).
|
||||||
|
|
|
@ -564,6 +564,19 @@ class GenericRelationsTests(TestCase):
|
||||||
for tag in tags:
|
for tag in tags:
|
||||||
self.assertSequenceEqual(tag.content_object.tags.all(), [tag])
|
self.assertSequenceEqual(tag.content_object.tags.all(), [tag])
|
||||||
|
|
||||||
|
def test_prefetch_related_custom_object_id(self):
|
||||||
|
tiger = Animal.objects.create(common_name='tiger')
|
||||||
|
cheetah = Animal.objects.create(common_name='cheetah')
|
||||||
|
Comparison.objects.create(
|
||||||
|
first_obj=cheetah, other_obj=tiger, comparative='faster',
|
||||||
|
)
|
||||||
|
Comparison.objects.create(
|
||||||
|
first_obj=tiger, other_obj=cheetah, comparative='cooler',
|
||||||
|
)
|
||||||
|
qs = Comparison.objects.prefetch_related('first_obj__comparisons')
|
||||||
|
for comparison in qs:
|
||||||
|
self.assertSequenceEqual(comparison.first_obj.comparisons.all(), [comparison])
|
||||||
|
|
||||||
|
|
||||||
class ProxyRelatedModelTest(TestCase):
|
class ProxyRelatedModelTest(TestCase):
|
||||||
def test_default_behavior(self):
|
def test_default_behavior(self):
|
||||||
|
|
Loading…
Reference in New Issue