用户模块
- 用户注册
- RESTful
- 数据开始
- 模型,数据库
- 创建用户
- 用户身份
- 管理员
- 普通
- 删除用户
- 用户身份
- 注册实现
- 添加了超级管理员生成
- 用户登陆
- 验证用户名密码
- 生成用户令牌
- 出现和注册公用post冲突
- 添加action
- path/?action=login
- path/?action=register
- 异常捕获尽量精确
- 用户认证
- BaseAuthentication
- authenticate
- 认证成功会返回 一个元组
- 第一个元素是user
- 第二元素是令牌 token,auth
- 认证成功会返回 一个元组
- authenticate
- BaseAuthentication
- 用户权限
- BasePermission
- has_permission
- 是否具有权限
- true拥有权限
- false未拥有权限
- has_permission
- BasePermission
- 用户认证和权限
- 直接配置在视图函数上就ok了
urls.py
from django.urls import path from UserAuthAndPermission import views urlpatterns = [ path('users/', views.UsersAPIView.as_view()), path('users/<int:pk>/', views.UserAPIView.as_view(), name='usermodel-detail'), ]
model.py
from django.db import models class UserModel(models.Model): u_name = models.CharField(max_length=32, unique=True) u_password = models.CharField(max_length=256) is_delete = models.BooleanField(default=False) is_super = models.BooleanField(default=False)
auth.py
from django.core.cache import cache from rest_framework.authentication import BaseAuthentication from UserAuthAndPermission.models import UserModel # 认证 class UserAuth(BaseAuthentication): def authenticate(self, request): # 判断请求类型,GET if request.method == 'GET': # 从客户端获取token token = request.query_params.get('token') # 从缓存中寻找token try: u_id = cache.get(token) user = UserModel.objects.get(pk=u_id) return user, token except: return
permission.py
from rest_framework.permissions import BasePermission from UserAuthAndPermission.models import UserModel # 用户权限判断,super返回True,其他返回false class IsSuperUser(BasePermission): # 重写的函数(非抽象类),最后有个返回 def has_permission(self, request, view): # 判断请求类型,GET if request.method == 'GET': if isinstance(request.user, UserModel): return request.user.is_super # return True return False # 不是GET,是有权限. return True
serializers.py
from rest_framework import serializers from UserAuthAndPermission.models import UserModel class UserSerializer(serializers.HyperlinkedModelSerializer): class Meta: model = UserModel fields = ('url', 'id', 'u_name', 'u_password', 'is_super')
views.py
import uuid from django.core.cache import cache from rest_framework import status, exceptions from rest_framework.generics import ListCreateAPIView from rest_framework.response import Response from DjangoREST.settings import SUPER_USERS from UserAuthAndPermission.auth import UserAuth from UserAuthAndPermission.constants import HTTP_ACTION_REGISTER, HTTP_ACTION_LOGIN from UserAuthAndPermission.models import UserModel from UserAuthAndPermission.permission import IsSuperUser from UserAuthAndPermission.serializers import UserSerializer # 创建用户 class UsersAPIView(ListCreateAPIView): serializer_class = UserSerializer queryset = UserModel.objects.all() # 设置只有登录用户才能获取用户列表 # 使用token验证用户登录,使用了认证类UserAuth authentication_classes = (UserAuth,) permission_classes = (IsSuperUser,) # 重写post,实现登录,路径中不出现动词,(出现冲突,和注册公用post) # 添加action def post(self, request, *args, **kwargs): # query_params相当于之前的GET,获取动作 action = request.query_params.get('action') # 根据接收到的动作,执行注册和登录 if action == HTTP_ACTION_REGISTER: return self.create(request, *args, **kwargs) elif action == HTTP_ACTION_LOGIN: u_name = request.data.get('u_name') u_password = request.data.get('u_password') try: user = UserModel.objects.get(u_name=u_name) if user.u_password == u_password: # 登录成功,生成身份令牌,16进制哈希码 # 宇宙唯一标识,.hex 将生成的uuid字符串中的 - 删除 token = uuid.uuid4().hex # 前后端分离,token不能存储在cookie和session(基于cookie)中 # 使用 缓存 或 数据库 来存储token,配置cache cache.set(token, user.id) data = { 'msg': 'login success', 'status': 200, 'token': token, } return Response(data) else: # 返回密码验证错误 raise exceptions.AuthenticationFailed except UserModel.DoesNotExist: raise exceptions.NotFound # 逻辑以外的异常错误 else: raise exceptions.ValidationError def create(self, request, *args, **kwargs): serializer = self.get_serializer(data=request.data) serializer.is_valid(raise_exception=True) self.perform_create(serializer) data = serializer.data u_name = data.get('u_name') # 若新建的用户名在预设的超级用户列表中,赋予super权限 if u_name in SUPER_USERS: print('创建超级用户') u_id = data.get('id') user = UserModel.objects.get(pk=u_id) user.is_super = True user.save() # 超级用户创建成功后,postman页面显示True data.update({'is_super': True}) headers = self.get_success_headers(serializer.data) return Response(data, status=status.HTTP_201_CREATED, headers=headers) # 查询用户,默认查询集合,超级管理员可以查 class UserAPIView(ListCreateAPIView): serializer_class = UserSerializer queryset = UserModel.objects.all()