django查询集在select语句中包含更多列
我一直在尝试使用查询集创建向后关系,并且连接工作正常,接受它不包括所选列中的其他连接表。下面是我的模型、查询集和查询。str() 打印
class Main(models.Model):
slug = models.SlugField()
is_active = models.BooleanField(default=True)
site = models.ForeignKey(Site)
parent = models.ForeignKey('self', blank=True, null=True, limit_choices_to={'parent' : None})
class Meta:
unique_together = (("slug", "parent"))
def __unicode__(self):
return self.slug
class MainI18n(models.Model):
main = models.ForeignKey(Main)
language = models.CharField(max_length=2, choices=settings.LANGUAGES)
title = models.CharField(max_length=100)
label = models.CharField(max_length=200, blank=True, null=True)
description = models.TextField(blank=True, null=True)
disclaimer = models.TextField(blank=True, null=True)
class Meta:
unique_together = (("language", "main"))
def __unicode__(self):
return self.title
class List(models.Model):
main = models.ForeignKey(Main)
slug = models.SlugField(unique=True)
is_active = models.BooleanField(default=True)
parent = models.ForeignKey('self', blank=True, null=True)
def __unicode__(self):
return self.slug
class ListI18n(models.Model):
list = models.ForeignKey(List)
language = models.CharField(max_length=2, choices=settings.LANGUAGES)
title = models.CharField(max_length=50)
description = models.TextField()
class Meta:
unique_together = (("language", "list"))
def __unicode__(self):
return self.title
和我的查询集
Main.objects.select_related('main', 'parent').filter(list__is_active=True, maini18n__language='en', list__listi18n__language='en')
,这就是我的查询打印的内容
'SELECT `category_main`.`id`, `category_main`.`slug`, `category_main`.`is_active`, `category_main`.`site_id`, `category_main`.`parent_id`, T5.`id`, T5.`slug`, T5.`is_active`, T5.`site_id`, T5.`parent_id` FROM `category_main` INNER JOIN `category_maini18n` ON (`category_main`.`id` = `category_maini18n`.`main_id`) INNER JOIN `category_list` ON (`category_main`.`id` = `category_list`.`main_id`) INNER JOIN `category_listi18n` ON (`category_list`.`id` = `category_listi18n`.`list_id`) LEFT OUTER JOIN `category_main` T5 ON (`category_main`.`parent_id` = T5.`id`) WHERE (`category_maini18n`.`language` = en AND `category_list`.`is_active` = True AND `category_listi18n`.`language` = en )'
任何人都可以帮助显示列表和 listi18n 中的列吗?我尝试了额外的方法,但它不允许我传递诸如category_list之类的东西。*
感谢
更新
感谢丹尼尔的方法,我设法让它工作,但我必须从ListI18n开始
ListI18n.objects.select_related('list', 'list__main', 'list__main__parent', 'list__main__i18nmain').filter(list__is_active=True, list__main__maini18n__language='en', language='en').query.__str__()
它现在工作完美,但我无法包含 list_main_maini18n,下面是输出查询
'SELECT `category_listi18n`.`id`, `category_listi18n`.`list_id`, `category_listi18n`.`language`, `category_listi18n`.`title`, `category_listi18n`.`description`, `category_list`.`id`, `category_list`.`main_id`, `category_list`.`slug`, `category_list`.`is_active`, `category_list`.`parent_id`, `category_main`.`id`, `category_main`.`slug`, `category_main`.`is_active`, `category_main`.`site_id`, `category_main`.`parent_id`, T5.`id`, T5.`slug`, T5.`is_active`, T5.`site_id`, T5.`parent_id` FROM `category_listi18n` INNER JOIN `category_list` ON (`category_listi18n`.`list_id` = `category_list`.`id`) INNER JOIN `category_main` ON (`category_list`.`main_id` = `category_main`.`id`) INNER JOIN `category_maini18n` ON (`category_main`.`id` = `category_maini18n`.`main_id`) LEFT OUTER JOIN `category_main` T5 ON (`category_main`.`parent_id` = T5.`id`) WHERE (`category_list`.`is_active` = True AND `category_listi18n`.`language` = en AND `category_maini18n`.`language` = en )'
知道如何在查询结果中包含 MainI18n 吗?我应该使用 extra 并包含表并在 where 子句中执行关系吗?或者有更好的方法吗?
I been trying to create a backward relation using queryset and the joining is working fine, accept that its not including the other joined table in the selected columns. Below is my models, queryset and query.str() print
class Main(models.Model):
slug = models.SlugField()
is_active = models.BooleanField(default=True)
site = models.ForeignKey(Site)
parent = models.ForeignKey('self', blank=True, null=True, limit_choices_to={'parent' : None})
class Meta:
unique_together = (("slug", "parent"))
def __unicode__(self):
return self.slug
class MainI18n(models.Model):
main = models.ForeignKey(Main)
language = models.CharField(max_length=2, choices=settings.LANGUAGES)
title = models.CharField(max_length=100)
label = models.CharField(max_length=200, blank=True, null=True)
description = models.TextField(blank=True, null=True)
disclaimer = models.TextField(blank=True, null=True)
class Meta:
unique_together = (("language", "main"))
def __unicode__(self):
return self.title
class List(models.Model):
main = models.ForeignKey(Main)
slug = models.SlugField(unique=True)
is_active = models.BooleanField(default=True)
parent = models.ForeignKey('self', blank=True, null=True)
def __unicode__(self):
return self.slug
class ListI18n(models.Model):
list = models.ForeignKey(List)
language = models.CharField(max_length=2, choices=settings.LANGUAGES)
title = models.CharField(max_length=50)
description = models.TextField()
class Meta:
unique_together = (("language", "list"))
def __unicode__(self):
return self.title
and my queryset is
Main.objects.select_related('main', 'parent').filter(list__is_active=True, maini18n__language='en', list__listi18n__language='en')
and this is what my query is printing
'SELECT `category_main`.`id`, `category_main`.`slug`, `category_main`.`is_active`, `category_main`.`site_id`, `category_main`.`parent_id`, T5.`id`, T5.`slug`, T5.`is_active`, T5.`site_id`, T5.`parent_id` FROM `category_main` INNER JOIN `category_maini18n` ON (`category_main`.`id` = `category_maini18n`.`main_id`) INNER JOIN `category_list` ON (`category_main`.`id` = `category_list`.`main_id`) INNER JOIN `category_listi18n` ON (`category_list`.`id` = `category_listi18n`.`list_id`) LEFT OUTER JOIN `category_main` T5 ON (`category_main`.`parent_id` = T5.`id`) WHERE (`category_maini18n`.`language` = en AND `category_list`.`is_active` = True AND `category_listi18n`.`language` = en )'
anyone can help show columns from list and listi18n? I tried extra but It doesn't allow me to pass things like category_list.*
thanks
UPDATE
Thanks for Daniel approach, I managed to get it to work but instead I had to start from ListI18n
ListI18n.objects.select_related('list', 'list__main', 'list__main__parent', 'list__main__i18nmain').filter(list__is_active=True, list__main__maini18n__language='en', language='en').query.__str__()
Its working perfectly now, but I couldn't include list_main_maini18n, below is the output query
'SELECT `category_listi18n`.`id`, `category_listi18n`.`list_id`, `category_listi18n`.`language`, `category_listi18n`.`title`, `category_listi18n`.`description`, `category_list`.`id`, `category_list`.`main_id`, `category_list`.`slug`, `category_list`.`is_active`, `category_list`.`parent_id`, `category_main`.`id`, `category_main`.`slug`, `category_main`.`is_active`, `category_main`.`site_id`, `category_main`.`parent_id`, T5.`id`, T5.`slug`, T5.`is_active`, T5.`site_id`, T5.`parent_id` FROM `category_listi18n` INNER JOIN `category_list` ON (`category_listi18n`.`list_id` = `category_list`.`id`) INNER JOIN `category_main` ON (`category_list`.`main_id` = `category_main`.`id`) INNER JOIN `category_maini18n` ON (`category_main`.`id` = `category_maini18n`.`main_id`) LEFT OUTER JOIN `category_main` T5 ON (`category_main`.`parent_id` = T5.`id`) WHERE (`category_list`.`is_active` = True AND `category_listi18n`.`language` = en AND `category_maini18n`.`language` = en )'
Any idea how can I include MainI18n in the query result? should I use extra and include the tables and do the relation in the where clause? or is there a better approach?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
从Main 到List 的关系是向后的ForeignKey(即FK 位于指向Main 的List 上),而
select_lated
则不能以这种方式工作。当你仔细想想,这是正确的:每个 Main 有许多 List,因此说“给我这个 Main 的一个 List”是没有意义的,这就是select_lated
的意思所有关于。如果您从列表开始,它会起作用:
因为这样您只关注转发关系。您可能会发现您可以重新排序视图/模板以通过这种方式使用查询。
The relationship from Main to List is a backwards ForeignKey (ie the FK is on List pointing at Main), and
select_related
doesn't work that way. When you think about it, this is correct: there are many Lists for each Main, so it doesn't make sense to say "give me the one List for this Main", which is whatselect_related
is all about.If you started from List, it would work:
because that way you're only following forwards relationships. You may find you're able to reorder your views/templates to use the query this way round.
在我看来它实际上正在工作(您的选择语句中的
T5
)。您始终可以通过my_obj.parent.is_active
之类的方式访问 django 中相关实例的字段。如果您在将它们包含在第一个查询中之前使用了select_lated
。如果您未在select_lated
中指定它,则对my_obj.parent.is_active
的调用将执行额外的数据库查询。Looks to me it is actually working (
T5
in your select statement). You can always access fields from related instances in django via something likemy_obj.parent.is_active
. If you usedselect_related
before they are included in the first query. If you didn't specify it inselect_related
a call tomy_obj.parent.is_active
for example would perform an extra db query.