У меня следующая структура модели:
class Container(models.Model):
pass
class Generic(models.Model):
name = models.CharacterField(unique=True)
cont = models.ManyToManyField(Container, null=True)
# It is possible to have a Generic object not associated with any container,
# thats why null=True
class Specific1(Generic):
...
class Specific2(Generic):
...
...
class SpecificN(Generic):
...
Скажем, мне нужно получить все модели Specific
, которые связаны с конкретным контейнером.
SQL для этого более или менее тривиален, но это не вопрос. К сожалению, я не очень опытен в работе с ORM (в частности, с ORM в Django), поэтому я могу пропустить шаблон здесь.
Когда сделано методом грубой силы, -
c = Container.objects.get(name='somename') # this gets me the container
items = c.generic_set.all()
# this gets me all Generic objects, that are related to the container
# Now what? I need to get to the actual Specific objects, so I need to somehow
# get the type of the underlying Specific object and get it
for item in items:
spec = getattr(item, item.get_my_specific_type())
это приводит к тонне попаданий в дБ (по одному для каждой общей записи, относящейся к контейнеру), так что это явно не тот способ, которым это можно сделать. Теперь, возможно, это можно сделать путем непосредственного получения объектов SpecificX:
s = Specific1.objects.filter(cont__name='somename')
# This gets me all Specific1 objects for the specified container
...
# do it for every Specific type
таким образом, БД будет поражен один раз для каждого конкретного типа (я думаю, это приемлемо).
Я знаю, что .select_related () не работает с отношениями m2m, поэтому здесь это не сильно поможет.
Повторюсь, конечный результат должен быть коллекцией объектов SpecificX (не Generic).