Django-filters 不适用于 Viewset

Posted

技术标签:

【中文标题】Django-filters 不适用于 Viewset【英文标题】:Django-filters does not work with the Viewset 【发布时间】:2019-02-21 07:01:57 【问题描述】:

我一直在尝试使用django-filters,但对象没有被过滤。此外,该权限不适用于 partial_update 视图

我有一个 Viewset,它具有一些基本操作,例如 - list()、retrieve()、destroy()、partial_update() 和其他一些操作,并尝试对其应用过滤器。

经过一些研究,我发现由于我是通过过滤器创建查询集,因此我必须重写 get_queryset() 方法。但是,这似乎也不起作用。过滤器是否仅适用于 ModelViewSetListApiView

ViewSet -

class PostViewSet(viewsets.ViewSet):
"""
The Endpoint to list, retrieve, create and delete Posts.

"""
filter_backends = (DjangoFilterBackend, )
# filterset_class = PostFilter
filter_fields = ('pet_age', 'pet_gender', 'breed')

def get_permissions(self):

    if self.action == 'partial_update' or self.action == 'update':
        permission_classes = [IsPostAuthor, ]

    elif self.action == 'create' or self.action == 'destroy':
        permission_classes = [IsAuthenticated, ]

    else:
        permission_classes = [AllowAny, ]

    return[permission() for permission in permission_classes]

def get_queryset(self):
    return Post.objects.active() # This is implemented via custom Manager

def list(self, request, *args, **kwargs):
    """
    Method for Post listing. It can be accessed by anyone.
    """

    serializer = PostListSerializer(self.get_queryset(), many=True, context="request": request)

    return Response(serializer.data)
# REST CODE TRUNCATED

权限 -

class IsPostAuthor(permissions.BasePermission):
"""
Object-level permission to only allow owners of an object to edit it.
"""

def has_object_permission(self, request, view, obj):
    if request.user.is_authenticated:
        if view.action in ['partial_update', 'update']:
            return obj.user.id == request.user.id
        return False

    return False

后过滤器 -

class PostFilter(filters.FilterSet):

class Meta:
    model = Post
    fields = ('pet_age', 'pet_gender', 'breed', )

经理 -

class PostManager(models.Manager):

def active(self):
    return self.filter(post_status='Active')

我们将不胜感激。

【问题讨论】:

“权限不起作用”是什么意思?看来您没有将IsPostAuthor 添加到视图中 我正在根据视图操作检查权限,即我想限制创建帖子的用户访问 partial_update() 方法(作者)。为此,我确实覆盖了 docs 中提到的 _ get_permissions() _ 【参考方案1】:

好的,所以终于从DRF Docs找到了解决方案。问题是在普通 ViewSet 的情况下,您必须重写方法 filter_queryset() 并相应地返回适当的 queryset。然后使用Aman 提到的 filter_queryset 下的 queryset -

serializer = PostListSerializer(self.filter_queryset(self.get_queryset()), many=True, context="request": request)

下面是代码供那些仍然面临问题的人参考 -

filter_queryset -

def filter_queryset(self, queryset):
    filter_backends = (DjangoFilterBackend, )

    # Other condition for different filter backend goes here

    for backend in list(filter_backends):
        queryset = backend().filter_queryset(self.request, queryset, view=self)
    return queryset

【讨论】:

您能否共享一个完整的视图集并覆盖查询集【参考方案2】:

你已经覆盖了 list 方法,所以调用 filter_queryet 方法不起作用。

def list(self, request, *args, **kwargs):
    """
     Method for Post listing. It can be accessed by anyone.
     """

    serializer = PostListSerializer(self.filter_queryset(self.get_queryset()), many=True, context= . 
     "request": request)

    return Response(serializer.data)

【讨论】:

感谢您的回复。但是,方法 filter_queryset() 是在 PostFilter 下实现的,因此我们不能将其引用为 self.filter_queryset()。另外,我尝试覆盖此方法,但这也没有用。我在想它是否与 ViewSet 有关。我应该通过 ModelViewSet 实现视图吗?? github.com/encode/django-rest-framework/blob/master/…,见 ListModelMixin ,它被称为 self.filter_queryset(self.get_queryset()) 是的,但我没有使用 mixin。无论如何,现在问题已经解决了。不过感谢您的投入。 viewsets.ViewSet is class is using that mixin

以上是关于Django-filters 不适用于 Viewset的主要内容,如果未能解决你的问题,请参考以下文章

TextAlignment 不适用于复选框

AJAX 不适用于 Django 应用程序

级联样式表不适用于角度Js

AngularJS 不适用于 MVC 局部视图

C# HttpClient PostAsync 不适用于 django rest 框架

Python 错误:此方法仅适用于类,不适用于实例