我们说我有两个模特。
模型
class Item(models.Model):
name = models.CharField(max_length=32)
# other fields
class ItemRelation(models.Model):
item = models.ForeignKey(Item, related_name='relations_item')
user = models.ForeignKey(User, related_name='relations_user')
has_viewed = models.BooleanField(default=False)
has_loved = models.BooleanFields(default=False)
现在,我想做的是想要使用django rest api获取所有项目的view_count和love_count。
views.py
class ItemView(ListAPIView):
queryset = Items.objects.all().prefetch_related(Prefetch('relations_item',
queryset=ItemRelation.objects.filter(Q(has_viewed=True) | Q(has_loved=True))
)
serializer_class = ItemSerializer
嗯,这是计划,但我完全不知道如何获取list-api-view中每个项目的view_count和love_count。我在序列化器上尝试了很多东西,但我认为它不会起作用。 然而,我可以使用SerializerMethod()来完成工作,但这将经历DB N + 1次。我已经阅读了文档和其他一些prefetch_related的博客,我能够轻松地做这件事,直到出现这个计数问题。
只是来自我的序列化程序的一个示例。
class ItemSerializer(serializers.ModelSerializer):
class Meta:
model = Item
fields = ['name', 'relations_item']
答案 0 :(得分:1)
我想你想计算a)has_viewed==True
和b)has_loved==True
的关系数量。
使用annotate()
与Django Conditional Expressions:
from django.db.models import Case, IntegerField, Sum, When
class ItemView(ListAPIView):
queryset = Items.objects.annotate(
view_count=Sum(
When(relations_item__has_viewed=True, then=1),
output_field=IntegerField(),
),
love_count=Sum(
When(relations_item__has_loved=True, then=1),
output_field=IntegerField(),
),
)
# ...