如何在django中将QuerySet过滤到每个组的最大成员?

问题描述 投票:0回答:1

模型是这样的:

class Application(models.Model):
    application_id = models.IntegerField()
    version_id = models.IntegerField()
    # some other attributes

其中application_idversion_id一起确定Application条目,因为一个应用程序可能有多个版本,并且具有最大version_id的条目是应用程序的当前版本。

目标是找到所有应用程序的当前版本。 SQL(在MySQL中)类似于:

SELECT
  *
FROM application AS app
WHERE version_id = (SELECT max(version_id)
                    FROM application
                    WHERE application_id = app.application_id);

怎么做到这一点?

请注意,这里的对象是过滤QuerySet,而不是仅获取最大的version_id,这将像使用GROUP BY一样简单,或者在django中使用values(),然后是annotate()。我也对当前版本的其他属性感兴趣。

python mysql django web orm
1个回答
2
投票

我自己想通了。 OuterRefSubQuery是诀窍,它是Django 1.11中的新功能,正如here所述。

from django.db.models import OuterRef, Subquery, F

def filter_to_current(qs: QuerySet):
    qs = qs.annotate(current=Subquery(qs.filter(application_id=OuterRef('application_id'))
                                          .order_by('-version_id').values('version_id')[:1])) \
            .filter(version_id=F('current'))
© www.soinside.com 2019 - 2024. All rights reserved.