2014-11-04 101 views
0

如何在不加入外键表的情况下订购与外键列相关的模型?通过外键的列为Django模型订购而无需连接外键表?

举例来说,如果我有:

class WidgetType(Model): 
    id = AutoField(primary_key=True) 
    label = CharField(max_length=16) 
    class Meta: 
     ordering = ["label"] 

class Widget(Model): 
    type = ForeignKey(WidgetType) 

怎样才能查询:

SELECT * FROM widgets_widget ORDER BY type_id 

如果没有外键表连接?

这似乎是<fk>_id不能使用:

>>> Widget.objects.all().order_by("type_id") 
FieldError: Cannot resolve keyword 'type_id' into field. Choices are: type 

使用<fk>__id似乎加入进来,然后忽略的FK表:

>>> print Widget.objects.all().order_by("type").query 
SELECT * FROM widgets_widget 
LEFT OUTER JOIN widgets_widgettype ON … 
ORDER BY widgets_widget.type_id 

而且使用<fk>使用外资关键型号的默认订购:

>>> print Widget.objects.all().order_by("type").query 
SELECT * FROM widgets_widget 
LEFT OUTER JOIN widgets_widgettype ON … 
ORDER BY widgets_widgettype.label 
+2

着Django的版本,您正在使用?看来只有django1.7提供了没有连接的order_by功能,你可以查看[这里](https://docs.djangoproject.com/en/dev/ref/models/querysets/#order-by) – 2014-11-04 07:32:56

+0

这是Django 1.5 。使用Django 1.7进行测试会产生相同的结果。 – 2014-11-06 18:10:03

+0

啊,是的,但它确实看起来像'.order_by(“type_id”)'将在1.7中有效! – 2014-11-06 18:11:21

回答

2

如果您是usin g Django 1.7,请参考Geo Jacob的答案 - 它包含在内。 如果不是,如果你不需要对象实例,你可以帮助自己与values()

class UserProfile(models.Model): 
    user = models.OneToOneField(User) 
    country = models.CharField(max_length=255) 


>>> qs = UserProfile.objects.all().values('user', 'country').order_by('user') 
>>> print qs.query 
SELECT `userprofiles_userprofile`.`user_id`, `userprofiles_userprofile`.`country` FROM `userprofiles_userprofile` ORDER BY `userprofiles_userprofile`.`user_id` ASC 
>>> qs 
[{'country': u'AT', 'user': 1L}, {'country': u'AT', 'user': 18L}, {'country': u'RU', 'user': 19L}, [...] 
+0

downvote有多荒谬? – schneck 2014-11-04 11:09:22

+0

将@David Wolever添加到黑名单:D – madzohan 2014-11-04 12:29:55

+0

不是我的失望,但这个答案也是不正确的。当您使用'.order_by('user')'时,将使用'User'模型的默认排序;看我的问题中的例子。 – 2014-11-06 18:06:44