#31863: FK field caching behavior change between 1.11.x and 2.x
-------------------------------------+-------------------------------------
Reporter: Gert | Owner: Gert Burger
Burger |
Type: Bug | Status: assigned
Component: Database | Version: 3.1
layer (models, ORM) |
Severity: Normal | Keywords:
Triage Stage: | Has patch: 0
Unreviewed |
Needs documentation: 0 | Needs tests: 0
Patch needs improvement: 0 | Easy pickings: 0
UI/UX: 0 |
-------------------------------------+-------------------------------------
Whilst upgrading a codebase from 1.11.x to 2.0/2.2 I noticed a weird
change in behavior of FK fields when copying model instances.
At the bottom of the post there is a testcase that succeeds on 1.11.x and
fails on 2.x
I think the commit that changed the behavior is
bfb746f983aa741afa3709794e70f1e0ab6040b5
So my question is two fold:
* Is the behavior in >=2.0 correct? It seems quite unexpected.
* What is the recommended way to clone a model instance? To date we have
been using copy() in a similar fashion to the test without issue. deepcopy
seems to work fine in >=2.0 but we haven’t done too much testing yet.
Test (placed in tests/model_fields/test_field_caching_change.py):
{{{#!python
import copy
from django.test import TestCase
from .models import Bar, Foo
class ForeignKeyCachingBehaviorTest(TestCase):
def test_copy(self):
foo1 = Foo.objects.create(a='foo1', d=1)
foo2 = Foo.objects.create(a='foo2', d=2)
bar1 = Bar.objects.create(a=foo1, b='bar1')
bar2 = copy.copy(bar1)
bar2.pk = None
bar2.a = foo2
# bar2 points to foo2
self.assertEqual(bar2.a, foo2)
self.assertEqual(bar2.a.id, bar2.a_id)
# bar1 is unchanged and must still point to foo1
# These fail on Django >= 2.0
self.assertEqual(bar1.a, foo1)
self.assertEqual(bar1.a.id, bar1.a_id)
}}}
and executed that via:
python3.6 tests/runtests.py --parallel 1 model_fields
In https://groups.google.com/g/django-
developers/c/QMhVPIqVVP4/m/mbezfaBEAwAJ Simon suggests:
> ..... Model.__copy__ should make sure to make a deep-copy of self._state
now that fields are cached in self._state.fields_cache.
which I will attempt to implement.
--
Ticket URL: <https://code.djangoproject.com/ticket/31863>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.
--
You received this message because you are subscribed to the Google Groups
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/django-updates/053.5dc81ec4add29cc41b01ba8f8fcacc74%40djangoproject.com.