Browse Source

Fixed #34633 -- Made create() method of reverse many-to-one managers clear prefetch_related() cache.

Aman Pandey 1 year ago
parent
commit
0fcd72bc48

+ 1 - 0
django/db/models/fields/related_descriptors.py

@@ -840,6 +840,7 @@ def create_reverse_many_to_one_manager(superclass, rel):
 
         def create(self, **kwargs):
             self._check_fk_val()
+            self._remove_prefetched_objects()
             kwargs[self.field.name] = self.instance
             db = router.db_for_write(self.model, instance=self.instance)
             return super(RelatedManager, self.db_manager(db)).create(**kwargs)

+ 1 - 0
docs/ref/models/querysets.txt

@@ -1259,6 +1259,7 @@ database.
 
     Also, if you call the database-altering methods
     :meth:`~django.db.models.fields.related.RelatedManager.add`,
+    :meth:`~django.db.models.fields.related.RelatedManager.create`,
     :meth:`~django.db.models.fields.related.RelatedManager.remove`,
     :meth:`~django.db.models.fields.related.RelatedManager.clear` or
     :meth:`~django.db.models.fields.related.RelatedManager.set`, on

+ 8 - 0
tests/many_to_one/tests.py

@@ -800,6 +800,14 @@ class ManyToOneTests(TestCase):
         # refs #21563
         self.assertFalse(hasattr(Article(), "reporter"))
 
+    def test_create_after_prefetch(self):
+        c = City.objects.create(name="Musical City")
+        d1 = District.objects.create(name="Ladida", city=c)
+        city = City.objects.prefetch_related("districts").get(id=c.id)
+        self.assertSequenceEqual(city.districts.all(), [d1])
+        d2 = city.districts.create(name="Goa")
+        self.assertSequenceEqual(city.districts.all(), [d1, d2])
+
     def test_clear_after_prefetch(self):
         c = City.objects.create(name="Musical City")
         d = District.objects.create(name="Ladida", city=c)