在settings.py
文件中,我编写了此设置:
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': (
'oauth2_provider.contrib.rest_framework.OAuth2Authentication',
),
'DEFAULT_PERMISSION_CLASSES': (
'rest_framework.permissions.IsAuthenticated',
),
}
[当我从password grant
应用程序调用带有令牌的任何API时,它工作正常,但是当我尝试从client credential grant
应用程序调用带有令牌的相同API时,它不起作用,并且响应403错误:
{ "detail": "You do not have permission to perform this action." }.
是由于默认权限吗?我不知道我必须使用什么权限!?
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': [
'rest_framework.authentication.TokenAuthentication', # <-- And here
],
}
INSTALLED_APPS = [
...
'rest_framework.authtoken'
]
这是您的用例的理想博客。https://www.django-rest-framework.org/api-guide/authentication/#tokenauthentication
permission
。 IsAuthenticated
权限检查使用request.user
授予时的None
,即client credential
。由于DRF中没有支持permission
授予的clien credential
,因此您必须使用自己的DRF custom permission。这就是我需要和使用的:from rest_framework.permissions import BasePermission
class IsAuthenticatedOrClientCredentialPermission(BasePermission):
def has_permission(self, request, view):
if request.auth is None:
return False
grant_type = request.auth.application.get_authorization_grant_type_display()
if request.user is None:
if grant_type == 'Client credentials':
request.user = request.auth.application.user # <-- this is because I needed to get the user either the grant is 'password' or 'client credentials'
return True
else:
return False
else:
return True
但是您可能只想检查授予类型是否为client credentials
并给予许可,如果是这样,这就是您所需要的:
from rest_framework.permissions import BasePermission class ClientCredentialPermission(BasePermission): def has_permission(self, request, view): if request.auth is None: return False grant_type = request.auth.application.get_authorization_grant_type_display() if request.user is None and grant_type == 'Client credentials': return True else: return False
注意:如果要使用第二个自定义权限,请注意
使用自定义权限:request.user
为None
,并且可以通过request.auth.application.user
获取客户端的所有者(向您发送请求)。 。您可以通过将自定义权限添加到适当的视图中来使用它们。 (就像在
rest_framework.permissions
下使用任何DRF权限一样)基于类的视图:
class ExampleView(APIView): permission_classes = [ClientCredentialPermission] # <-- Add your permissions to this list def get(self, request, format=None): content = { 'status': 'request was permitted' } return Response(content)
基于功能的视图:
@api_view(['GET']) @permission_classes([ClientCredentialPermission]) # <-- Add your permissions to this list def example_view(request, format=None): content = { 'status': 'request was permitted' } return Response(content)