显示组权限导致django中的重复查询

时间:2017-01-10 05:58:27

标签: django postgresql django-rest-framework

TLDR:我想序列化一个组及其权限名称。但是发生了许多来自权限模型的content_type的重复查询。我试图通过预取来解决它,但没有奏效。我做错了什么?

所以我的下载方法的序列化器如下所示

class RetrieveGroupSerializer(serializers.ModelSerializer):
    user_set = UserSerializer(many=True, read_only=True)
    permissions = PermissionsSerializer(many=True, read_only=True)

    class Meta:
        model = Group
        fields = ('name', 'user_set', 'permissions')

列表方法的序列化器如下所示

class GroupSerializer(serializers.ModelSerializer):
    user_set = UserSerializer(many=True)
    permissions = PermissionsSerializer(many=True)

    class Meta:
        model = Group
        fields = ('url', 'user_set', 'permissions')

观点见下文

class GroupViewSet(
                   mixins.CreateModelMixin,
                   mixins.RetrieveModelMixin,
                   mixins.UpdateModelMixin,
                   mixins.ListModelMixin,
                   viewsets.GenericViewSet):
    """
    Creates, Updates, and retrives User Groups
    """

    queryset = Group.objects.all().prefetch_related('user_set').prefetch_related('permissions__content_type')
    serializer_class = GroupSerializer
    permission_classes = (
        IsAuthenticated,
    )
    action_serializer_classes = {
        "create": CreateGroupSerializer,
        "retrieve": RetrieveGroupSerializer,
        "update": UpdateGroupSerializer
    }

    def get_serializer_class(self):
        try:
            return self.action_serializer_classes[self.action]
        except (KeyError, AttributeError):
            return super(GroupViewSet, self).get_serializer_class()

当我使用list方法时,我没有遇到任何重复的查询,但是当我在任何单个组实例上使用retrieve方法时,我会遇到很多重复的查询。 django-debug-toolbar output

正如您所看到的,Permission Model中的content_type被查询了62次。 所以我在权限模型中的外键上使用了prefetch_related。但结果是一样的。

但是相同的查询集对List方法很有效,并且不会导致重复查询。你可以在下面看到 enter image description here

除了重复查询的问题,我也很困惑,同一个查询集怎么会导致这样不同的结果呢?

1 个答案:

答案 0 :(得分:2)

这可能是因为可浏览的API还会显示一个创建/更新表单,其中包含内容类型的下拉列表,并且不会使用预取优化。 尝试将其作为JSON获取,并查看它执行的请求数量或删除更新权限,以查看它是否更改了查询数量。