Django:删除使用extra()方法添加的GROUP BY?

时间:2009-09-03 11:34:37

标签: python sql django django-models photologue

嗨(对不起我的英语不好)!

当我这样做时:

gallery_qs = Gallery.objects.all()\
                    .annotate(Count('photos'))\
                    .extra(select={'photo_id': 'photologue_photo.id'})

sql查询是:

SELECT (photologue_photo.id) AS `photo`, `photologue_gallery`.*
FROM `photologue_gallery` 
    LEFT OUTER JOIN `photologue_gallery_photos` 
      ON (`photologue_gallery`.`id` = `photologue_gallery_photos`.`gallery_id`) 
    LEFT OUTER JOIN `photologue_photo` 
      ON (`photologue_gallery_photos`.`photo_id` = `photologue_photo`.`id`) 
GROUP BY `photologue_gallery`.`id`, photologue_photo.id 
ORDER BY `photologue_gallery`.`publication_date` DESC

问题是extra方法会自动在GROUP BY子句中添加photologue_photo.id。我需要删除它,因为它复制了画廊,例如:

[<Gallery: Lorem ipsum dolor sit amet>, <Gallery: Lorem ipsum dolor sit amet>, <Gallery: Lorem ipsum dolor sit amet>, <Gallery: Lorem ipsum dolor sit amet>, <Gallery: Lorem ipsum dolor sit amet>, <Gallery: Lorem ipsum dolor sit amet>, <Gallery: Lorem ipsum dolor sit amet>]

我需要用django进行此查询,是否可能?

SELECT (photologue_photo.id) AS `photo`, `photologue_gallery`.*
FROM `photologue_gallery` 
    LEFT OUTER JOIN `photologue_gallery_photos` 
      ON (`photologue_gallery`.`id` = `photologue_gallery_photos`.`gallery_id`) 
    LEFT OUTER JOIN `photologue_photo` 
      ON (`photologue_gallery_photos`.`photo_id` = `photologue_photo`.`id`) 
GROUP BY `photologue_gallery`  
ORDER BY `photologue_gallery`.`publication_date` DESC

谢谢! :)

2 个答案:

答案 0 :(得分:1)

我认为你真的不需要额外的东西。从Django的概念来看,你不需要在运行Django QuerySet时挑选特定的列。这个逻辑可以在模板方面完成。

我假设您知道如何从您的视图中将galley_qs推送到您的模板:

# views.py
gallery_qs = Gallery.objects.all()\
                .annotate(Count('photos'))

在你的模板/ html中:

{% for gallery in gallery_qs %}
    {% for photo in gallery.photos %}

    {% endfor %}
{% endfor %}

photos是您的图库模型中的ManyToManyField。

答案 1 :(得分:0)

为什么当图库到照片ID是多对多的关系时,您是否尝试使用带有photo_id的不同画廊记录?据我所知,您正在进行的查询只能获得每个图库的单个照片ID。

如果您确实需要执行上述操作,我认为您可以使用distinct()来获取不同的图库记录(顺便说一句,您不需要其中的“all()”。

Gallery.objects.distinct()\
               .annotate(Count('photos'))\
               .extra(select={'photo_id': 'photologue_photo.id'})

或者您只需直接访问照片ID,

g = Gallery.objects.annotate(Count('photos'))
# Get the photo
photo = g.photos[0]