在django rest框架序列化器中优化django相关集合平均值

时间:2015-07-16 10:36:04

标签: django postgresql caching optimization django-rest-framework

我正在使用Django 1.8和Django Rest Framework。 我有两个模型:MarkerMarkerComment

class Marker(models.Model):
    # a bunch of fields here...

    def rating(self):
        """
        Return the mean rating from all comments
        """
        return self.comments.aggregate(models.Avg('rating'))['rating__avg']


class MarkerComment(models.Model):
    # a few fields here...

    marker = models.ForeignKey(Marker, blank=False, related_name='comments')    
    rating = models.PositiveSmallIntegerField(blank=False)

在我的序列化程序中,我有类似的东西:

class MarkerSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model = Marker
        fields = (
            'url', 'pk', 'created', 'name', 'category', 'rating', ...
        )
        read_only_fields = ('rating')

我的序列化程序上的list查询时间过长,因为它查询每个标记以获得平均值。见NewRelic:

New Relic graph, it's very slow 1,800ms average

这是我的结果集中每个标记运行的查询:

SELECT AVG("maps_markercomment"."rating") AS "rating__avg" FROM "maps_markercomment" WHERE "maps_markercomment"."marker_id" = 1788

如果我没有使用Django Rest Framework,我可能会做一些事情来立即获得所有评级

Marker.objects.filter(...).annotate(rating=Avg('comments__rating'))

所以我的问题是:我有什么选择让它更快?有没有办法在仍然使用序列化程序的同时在单个SQL查询中拥有所有这些?如何缓存每个标记的评级?

1 个答案:

答案 0 :(得分:1)

您可以将所需的优化应用于视图中的查询集,因为此优化的查询集最终将传递给序列化程序。