# models class User(models.Model): name = models.CharField(max_length=32) pwd = models.CharField(max_length=64) user_type = models.IntegerField(choices=((1, "超級管理員"), (2, "普通管理員"), (3, "2b用戶")), default=3) # 跟User表作一對一關聯 class Token(models.Model): user = models.OneToOneField(to='User') token = models.CharField(max_length=64)
# MyAuths.py 自定義認證邏輯代碼 class MyAuth(BaseAuthentication): def authenticate(self, request): # 寫認證的邏輯 token = request.GET.get('token') token_obj = models.Token.objects.filter(token=token).first() if token_obj: # 可以取到值,表示已經登陸了 print("驗證登陸經過") return token_obj.user, token_obj else: # 沒有取到值,表示沒有登陸,往外拋異常 raise AuthenticationFailed('尚未登陸呦')
# views.py 視圖部分邏輯 from rest_framework.views import APIView from app01 import models import uuid # 用來生成惟一token from django.core.exceptions import ObjectDoesNotExist from rest_framework.response import Response from app01.MyAuths import MyAuth # Create your views here. class Books(APIView): # 局部認證, 源碼中的 authentication_classes 部分,執行列表中的認證邏輯 # 執行優先級爲:最高是此處定義的視圖類中定義的 ---> 若是沒有,就去項目settings.py中查找 ---> 都沒有就選擇rest_framework默認的配置文件中取 authentication_classes = [MyAuth, ] def get(self, request): # request.user 就是當前登陸用戶 print(request.user.name) # 'AnonymousUser' object has no attribute 'name' # 上面語句後面的錯誤,是由於原先將 authentication_classes = [MyAuth, ] 這句代碼放進了get方法裏面了 # print(request.user.name, type(request.user)) return Response('這個是驗證過登陸而返回的的信息!') class Login(APIView): def post(self, request): response = {'code': 100, 'msg': '登陸成功'} name = request.data.get('name') pwd = request.data.get('pwd') try: user = models.User.objects.filter(name=name, pwd=pwd).get() # 登陸成功,須要將token寫進token表中 # 生成一個惟一的token id token = uuid.uuid4() models.Token.objects.update_or_create(user=user, defaults={'token': token}) response['token'] = token except ObjectDoesNotExist as e: response['code'] = 101 response['msg'] = '用戶名或者密碼錯誤' except Exception as e: response['code'] = 102 response['msg'] = str(e) return Response(response)
# MyAuths.py 權限邏輯部分 class MyPermision(BasePermission): message = '不是超級用戶,查看不了' def has_permission(self,request,view): if request.user.user_type==1: return True else: return False
# views.py 視圖邏輯部分 class Publish(APIView): # authentication_classes = [] 在setting.py裏面設置了全局的token認證, authentication_classes = [MyAuth, ] permission_classes = [MyPermision, ] def get(self, request): # print(request.user.name) return Response('返回了全部出版社信息')