Opened 6 years ago

Closed 4 months ago

Last modified 3 weeks ago

#15250 closed Bug (fixed)

Cannot fill parent model instance in cache

Reported by: Vlastimil Zíma Owned by: Paulo
Component: Database layer (models, ORM) Version: 1.2
Severity: Normal Keywords:
Cc: Triage Stage: Accepted
Has patch: yes Needs documentation: no
Needs tests: no Patch needs improvement: yes
Easy pickings: no UI/UX: no

Description

Continue of #14371
I tried again in django trunk (tested also in 1.2.4)

I have following models (in SQLite3)

class Parent(models.Model):
    parent_int = models.IntegerField()

class Child(Parent):
    child_int = models.IntegerField()
In [1]: from django.db import connection

In [2]: from testmodule.models import Parent, Child

In [3]: Child.objects.create(parent_int = 1, child_int = 2)
Out[3]: <Child: Child object>

In [4]: Child.objects.get(parent_int = 1, child_int = 2).parent_ptr
Out[4]: <Parent: Parent object>

In [5]: connection.queries
Out[5]: 
[{'sql': u'INSERT INTO "testmodule_parent" ("parent_int") VALUES (1)',
  'time': '0.001'},
 {'sql': u'INSERT INTO "testmodule_child" ("parent_ptr_id", "child_int") VALUES (2, 2)',
  'time': '0.000'},
 {'sql': u'SELECT "testmodule_parent"."id", "testmodule_parent"."parent_int", "testmodule_child"."parent_ptr_id", "testmodule_child"."child_int" FROM "testmodule_child" INNER JOIN "testmodule_parent" ON ("testmodule_child"."parent_ptr_id" = "testmodule_parent"."id") WHERE ("testmodule_parent"."parent_int" = 1  AND "testmodule_child"."child_int" = 2 )',
  'time': '0.000'},
 {'sql': u'SELECT "testmodule_parent"."id", "testmodule_parent"."parent_int" FROM "testmodule_parent" WHERE "testmodule_parent"."id" = 2 ',
  'time': '0.000'}]

In [6]: Child.objects.select_related('parent').get(parent_int = 1, child_int = 2).parent_ptr
Out[6]: <Parent: Parent object>

In [7]: connection.queries
Out[7]: 
[{'sql': u'INSERT INTO "testmodule_parent" ("parent_int") VALUES (1)',
  'time': '0.001'},
 {'sql': u'INSERT INTO "testmodule_child" ("parent_ptr_id", "child_int") VALUES (2, 2)',
  'time': '0.000'},
 {'sql': u'SELECT "testmodule_parent"."id", "testmodule_parent"."parent_int", "testmodule_child"."parent_ptr_id", "testmodule_child"."child_int" FROM "testmodule_child" INNER JOIN "testmodule_parent" ON ("testmodule_child"."parent_ptr_id" = "testmodule_parent"."id") WHERE ("testmodule_parent"."parent_int" = 1  AND "testmodule_child"."child_int" = 2 )',
  'time': '0.000'},
 {'sql': u'SELECT "testmodule_parent"."id", "testmodule_parent"."parent_int" FROM "testmodule_parent" WHERE "testmodule_parent"."id" = 2 ',
  'time': '0.000'},
 {'sql': u'SELECT "testmodule_parent"."id", "testmodule_parent"."parent_int", "testmodule_child"."parent_ptr_id", "testmodule_child"."child_int" FROM "testmodule_child" INNER JOIN "testmodule_parent" ON ("testmodule_child"."parent_ptr_id" = "testmodule_parent"."id") WHERE ("testmodule_parent"."parent_int" = 1  AND "testmodule_child"."child_int" = 2 )',
  'time': '0.000'},
 {'sql': u'SELECT "testmodule_parent"."id", "testmodule_parent"."parent_int" FROM "testmodule_parent" WHERE "testmodule_parent"."id" = 2 ',
  'time': '0.000'}]

You can see that query is correct for selecting parent, but it's instance is not created in cache as usual and that leads to another select.

Attachments (1)

fill_parent_model_instance_1.diff (4.1 KB) - added by marekw2143 6 years ago.

Download all attachments as: .zip

Change History (15)

comment:1 Changed 6 years ago by Russell Keith-Magee

Needs documentation: unset
Needs tests: unset
Patch needs improvement: unset
Triage Stage: UnreviewedAccepted

Ok - thanks for the extra debug information. Looks like there is something going wrong here. As I indicated on #14371, the select_related() isn't necessary, but you've clearly shown that the parent object isn't being prepopulated as I said, either.

As a matter of procedure -- this is the sort of situation where it would have been ok to reopen the old ticket. It's the same problem, but by providing more debugging information you can demonstrate that the assertion I made was wrong. If that's the case, its perfectly acceptable to reopen an old ticket.

comment:2 Changed 6 years ago by marekw2143

Owner: changed from nobody to marekw2143
Status: newassigned

Changed 6 years ago by marekw2143

comment:3 Changed 6 years ago by marekw2143

Has patch: set

comment:4 Changed 5 years ago by Łukasz Rekucki

Severity: Normal
Type: Bug

comment:5 Changed 5 years ago by Julien Phalip

Needs tests: set

comment:6 Changed 5 years ago by Aymeric Augustin

Easy pickings: unset

See #16043 for a similar bug that has a test case.

comment:7 Changed 5 years ago by marekw2143

Owner: marekw2143 deleted
Status: assignednew
UI/UX: unset

comment:8 Changed 5 months ago by Tim Graham

I closed #26523 as a duplicate (but it should be confirmed when solving this ticket).

comment:9 Changed 4 months ago by Paulo

Owner: set to Paulo
Status: newassigned

comment:10 Changed 4 months ago by Paulo

Needs tests: unset

comment:11 Changed 4 months ago by Tim Graham

Patch needs improvement: set

PR with some comments for improvement.

comment:12 Changed 4 months ago by Tim Graham <timograham@…>

Resolution: fixed
Status: assignedclosed

In 38575b00:

Fixed #15250 -- Avoided extra query on some multi-table inheritance queries.

Thanks marekw2143 for the initial patch and carljm for support.

comment:13 Changed 4 months ago by Tim Graham <timograham@…>

In 3e9f769:

Refs #15250 -- Added docstring for ForwardOneToOneDescriptor.

comment:14 Changed 3 weeks ago by Simon Charette <charette.s@…>

In 0bbab97:

Refs #15250 -- Removed an obsolete comment regarding MTI cascade deletion.

Note: See TracTickets for help on using tickets.
Back to Top