在DRF中拒绝权限时返回自定义消息

Bob*_*Dem 8 django permissions django-rest-framework

Django REST Framework一个关于权限的优秀文档.我已经能够使用预先制作的权限类,并且还构建了自己的权限.

但是,有一些API方法,其中"权限被拒绝"通用消息对用户来说不是很有用.例如,如果用户已通过身份验证但帐户已过期,那么让用户知道他的帐户已过期而不仅仅是权限被拒绝错误会更好.

在构建自定义权限类时,您可以返回TrueFalse- 根据文档.但是,如上所述,我希望向用户显示更多信息.怎么做到这一点?

Sek*_*kai 15

从DRF 3.2.0开始,您只需要添加一个消息属性:

from rest_framework import permissions

class CustomerAccessPermission(permissions.BasePermission):
    message = 'Adding customers not allowed.'

    def has_permission(self, request, view): 
Run Code Online (Sandbox Code Playgroud)

请参阅DRF文档:http://www.django-rest-framework.org/api-guide/permissions/#custom-permissions


bzd*_*111 10

当未授予权限时,我将引发自定义响应的异常。它适用于 djangorestframewor(3.10.1) 和 django(2.2.3)。

from rest_framework.permissions import BasePermission
from rest_framework.exceptions import APIException
from rest_framework import status


class IsLogin(BasePermission):
    """
    Allows access only to authenticated users.
    """

    def has_permission(self, request, view):
        if request.email:
            return True
        raise NeedLogin()


class NeedLogin(APIException):
    status_code = status.HTTP_403_FORBIDDEN
    default_detail = {'error': True, 'message': 'need login'}
    default_code = 'not_authenticated'
Run Code Online (Sandbox Code Playgroud)


Dru*_*lan 6

From DRF

you can simply add message attribute.

from rest_framework import permissions

class IsSuperUserPermission(permissions.BasePermission):
    message = 'User is not superuser'

    def has_permission(self, request, view):
        return self.request.user.is_superuser
Run Code Online (Sandbox Code Playgroud)

It will return a dict with key detail, something like this:

{
    'detail': 'User is not superuser'
}
Run Code Online (Sandbox Code Playgroud)

But what if you want for example that the dict key not to be detail but errors for example, it will be the same how return errors DRF.

We can set message attribute not to string but to dict, something like this:

class IsSuperUserPermission(permissions.BasePermission):
    message = {'errors': ['User is not a superuser']}

    def has_permission(self, request, view):
        self.message['errors'].clear()
        return self.request.user.is_superuser
Run Code Online (Sandbox Code Playgroud)

In this case the error will be:

{
    'errors': ['User is not a superuser']
}
Run Code Online (Sandbox Code Playgroud)