自定义认证类、权限类
自定义认证类,自定义权限类
一 自定义认证类
思路:
实现了自己确定身份的方式
1 定制自己的token串格式
2 应用drf-token里面的方法来实现token解密
3 然后写写确定身份的逻辑
urls.py
ps 主要是测一个post就行了
# 3 认证组件的使用
url(r'^v3/cars/$', views.CarV3ModelViewSet.as_view({
'get': 'list',
'post': 'create'
})),
url(r'^v3/cars/(?P<pk>.*)/$', views.CarV3ModelViewSet.as_view({
'get': 'retrieve',
'put': 'update',
'patch': 'partial_update',
'delete': 'destroy',
})),
api/authentications.py
具体实现了,直接前台headers里 auth:asdffasdf.asdfa.sdfasdf;的格式。
认证类,无非就是确定身份 游客和管理员 ,可以使用request.user来查看身份。
from rest_framework.authentication import BaseAuthentication
from rest_framework.exceptions import AuthenticationFailed
import jwt
from rest_framework_jwt.authentication import BaseJSONWebTokenAuthentication
from rest_framework_jwt.authentication import jwt_decode_handler
class JWTAuthentication(BaseJSONWebTokenAuthentication):
# 自定义认证类,重写authenticate方法
def authenticate(self, request):
# 认证通过,返回user,auth,自定义改成了auth
# 认证失败,返回None
# 直接前台headers里 auth:asdffasdf.asdfa.sdfasdf;
auth = request.META.get('HTTP_AUTH') # 前台用auth携带token
# print(auth)
if not auth:
return None
try:
payload = jwt_decode_handler(auth)
# 出现jwt解析异常,直接抛出异常,代表非法用户,也可以返回None,作为游客处理
except jwt.ExpiredSignature:
raise AuthenticationFailed('token已过期')
except:
raise AuthenticationFailed('token-非法')
# 根据token获取user
user = self.authenticate_credentials(payload)
return (user, auth)
settings.py
REST_FRAMEWORK = {
# Base API policies
'DEFAULT_AUTHENTICATION_CLASSES': [
'api.authentications.JWTAuthentication',
],}
views.py
# 局部使用认证组件
from . import serializers
from rest_framework.viewsets import ModelViewSet
from rest_framework_jwt.authentication import JSONWebTokenAuthentication
from rest_framework.permissions import IsAuthenticatedOrReadOnly
class CarV3ModelViewSet(ModelViewSet):
# 认证组件的token格式是 在Headers里添加字段 authorization:jwt sdfj.jasdf.xxyandls
authentication_classes = [JSONWebTokenAuthentication] # 用token确定身份 游客 or 登录用户 用request.user来确定,
# ps:如果认证通过可以通过request.user 来拿到user djangoorm对象 如request.user
permission_classes = [IsAuthenticatedOrReadOnly] # 根据身份确定权限
queryset = models.Car.objects.filter(is_delete=False)
serializer_class = serializers.CarModelSerializer
def destroy(self, request, *args, **kwargs):
obj = self.get_object()
obj.is_delete = True
obj.save()
return Response('删除成功')
postman测试
二 自定义权限类
思路:
实现了自己根据身份验证权限的方式
有权限,返回True
无权限,返回False
1 是否是用户
2 如果是用户是否在管理员组中
满足以上两点通过权限认证
usl.py
# 管理员分组成员才可以查看所以用户信息
url(r'^users/$', views.UserListAPIView.as_view()),
api/permissions.py
from rest_framework.permissions import BasePermission
class AdminPermission(BasePermission):
# 继承BasePermission,重写has_permission
def has_permission(self, request, view):
# 有权限,返回True
# 无权限,返回False
user = request.user
if not user:
return False
# 用户是 管理员 分组 (管理员分组是Group表中的一条自定义记录)
# 定位到了哪张表哪一张表就可以直接filter了
if not user.groups.filter(name='管理员'):
return False
# 登录的用户必须是自定义管理员分组成员
return True
views.py
from rest_framework.generics import ListAPIView
from rest_framework.permissions import IsAdminUser
from .permissions import AdminPermission
from rest_framework.throttling import AnonRateThrottle, UserRateThrottle
class UserListAPIView(ListAPIView):
queryset = models.User.objects.filter(is_active=True)
serializer_class = serializers.UserModelSerializer
# 登录的用户必须是自定义管理员分组成员
permission_classes = [AdminPermission]