django orm每个外键的最新项目组
django orm latest item group by each foreign key
我们有以下型号:
class Publisher(models.Model):
name = models.CharField(max_length=32)
local_name = models.CharField(max_length=32)
url_pattern = models.CharField(max_length=128)
enabled = models.BooleanField(default=True)
home_page = models.BooleanField(default=False)
category = models.ForeignKey(NewspaperCategory, null=True)
class Newspaper(models.Model):
class Meta:
unique_together = ("publisher", "date")
ordering = ("-date",)
publisher = models.ForeignKey(Publisher)
image = models.ImageField(upload_to=newspaper_upload_to)
thumbnail = models.ImageField(upload_to=newspaper_thumbnail_upload_to)
date = models.DateField()
我有一个 APIView
(Django 休息框架),有几个不同的查询参数可以过滤 API 的输出。我想要一个 "latest" 查询参数,它只列出每个发布者的最新版本。此外,在评估之前,我需要能够对该 QuerySet
进行进一步的过滤和切片。
但是查询的结果应该是 Newspaper 实例而不是 dict
所以我可以将它们提供给我的序列化程序。
我现在的观点是这样的:
class Newspapers(APIView):
def get(self, request):
queryset = models.Newspaper.objects.filter(deleted=False).prefetch_related('publisher')
if "latest" in request.GET:
# doing something here with queryset
if "publisher_id" in request.GET:
queryset = queryset.filter(publisher_id=request.GET['publisher_id'])
if "category" in request.GET:
queryset = queryset.filter(publisher__category_id=request.GET['category'])
if "before" in request.GET:
queryset = queryset.filter(date__lt=request.GET['before'])
if "after" in request.GET:
queryset = queryset.filter(date__gte=request.GET['after'])
if "home_page" in request.GET:
queryset = queryset.filter(publisher__home_page=request.GET['home_page'].lower() == 'true')
queryset = queryset.order_by('-date', 'publisher__order')
return PagingResponse(
request,
serializers.NewspaperVersionSerializer,
query=queryset,
identifier_name='date'
)
我们可以通过两个查询来做到这一点:
if "latest" in request.GET:
latest_ids = list( # <-- first query
queryset.order_by('id')
.values('publisher_id')
.annotate(id=Max('id'))
.values_list('id', flat=True)
)
queryset = queryset.filter(id__in=latest_ids) # <-- second query
第一个查询获取出版商最新报纸组的列表,第二个查询获取这些报纸的查询集以进一步过滤、切片和...
我们有以下型号:
class Publisher(models.Model):
name = models.CharField(max_length=32)
local_name = models.CharField(max_length=32)
url_pattern = models.CharField(max_length=128)
enabled = models.BooleanField(default=True)
home_page = models.BooleanField(default=False)
category = models.ForeignKey(NewspaperCategory, null=True)
class Newspaper(models.Model):
class Meta:
unique_together = ("publisher", "date")
ordering = ("-date",)
publisher = models.ForeignKey(Publisher)
image = models.ImageField(upload_to=newspaper_upload_to)
thumbnail = models.ImageField(upload_to=newspaper_thumbnail_upload_to)
date = models.DateField()
我有一个 APIView
(Django 休息框架),有几个不同的查询参数可以过滤 API 的输出。我想要一个 "latest" 查询参数,它只列出每个发布者的最新版本。此外,在评估之前,我需要能够对该 QuerySet
进行进一步的过滤和切片。
但是查询的结果应该是 Newspaper 实例而不是 dict
所以我可以将它们提供给我的序列化程序。
我现在的观点是这样的:
class Newspapers(APIView):
def get(self, request):
queryset = models.Newspaper.objects.filter(deleted=False).prefetch_related('publisher')
if "latest" in request.GET:
# doing something here with queryset
if "publisher_id" in request.GET:
queryset = queryset.filter(publisher_id=request.GET['publisher_id'])
if "category" in request.GET:
queryset = queryset.filter(publisher__category_id=request.GET['category'])
if "before" in request.GET:
queryset = queryset.filter(date__lt=request.GET['before'])
if "after" in request.GET:
queryset = queryset.filter(date__gte=request.GET['after'])
if "home_page" in request.GET:
queryset = queryset.filter(publisher__home_page=request.GET['home_page'].lower() == 'true')
queryset = queryset.order_by('-date', 'publisher__order')
return PagingResponse(
request,
serializers.NewspaperVersionSerializer,
query=queryset,
identifier_name='date'
)
我们可以通过两个查询来做到这一点:
if "latest" in request.GET:
latest_ids = list( # <-- first query
queryset.order_by('id')
.values('publisher_id')
.annotate(id=Max('id'))
.values_list('id', flat=True)
)
queryset = queryset.filter(id__in=latest_ids) # <-- second query
第一个查询获取出版商最新报纸组的列表,第二个查询获取这些报纸的查询集以进一步过滤、切片和...