drf08(代码片段)

bigb bigb     2023-04-30     314

关键词:

三大认证

流程

技术图片

  • 由于DRF中, 所有的视图类都要直接和间接继承APIView类, 也只有APIView类中才有dispatch方法, 所以所有的请求都要经过三大认证, 认证通过后执行相应请求的视图函数
def dispatch(self, request, *args, **kwargs):
     
    "..."   
    
    try:
        # 三大认证
        self.initial(request, *args, **kwargs)
        
        "..."   

    except Exception as exc:
            # 异常处理
            response = self.handle_exception(exc)
            
            
            
def initial(self, request, *args, **kwargs):
    
    "..."   
       
    # 认证
    self.perform_authentication(request)
    # 权限
    self.check_permissions(request)
    # 频率
    self.check_throttles(request)
  1. 认证组件
  • 请求未携带token ==> 游客
  • 请求携带token
    • token认证通过 ==> 合法用户
    • token认证未通过 ==> 非法用户
  1. 权限组件
  • 游客权限
  • 登录用户权限
  1. 频率组件
  • 限制
  • 不限制

认证组件

  1. DRF认证类的默认配置
# rest_framework/settings.py
'DEFAULT_AUTHENTICATION_CLASSES': [
        # 默认采用的session认证
        'rest_framework.authentication.SessionAuthentication',
        'rest_framework.authentication.BasicAuthentication'
  1. 自定义认证类
    1. 继承BaseAuthentication
    2. 重写authenticate方法
    3. 方法体
      1. 从请求头HTTP_AUTHORIZATION中拿token
      2. 没有token返回None, 游客
      3. 有token, 校验不通过, 抛AuthenticationFailed异常, 非法用户
      4. 有token, 校验通过, 返回(user, token), 合法用户
# authentications.py
from rest_framework.authentication import BaseAuthentication
from rest_framework.exceptions import AuthenticationFailed


# 自定义认证类继承BaseAuthentication
class MyAuthentication(BaseAuthentication):
    """
    1.从请求中获取token(一般是HTTP_AUTHORIZATION)
    2.token为None, 返回None, ==> 游客
    3.token不为None
        认证失败, raise AuthenticationFailed(''), ==> 非法用户
        认证通过, 返回(user, token)或者(user, None), ==> 合法用户
    """
    def authenticate(self, request):
        pass
  1. 全局配置认证类
# settings.py
REST_FRAMEWORK = 
    # 全局配置认证类
    'DEFAULT_AUTHENTICATION_CLASSES': [     
        'api.authentications.MyAuthentication',
        'rest_framework.authentication.BasicAuthentication',
    ]

权限组件

  1. DRF权限类的默认配置
# rest_framework/settings.py
'DEFAULT_PERMISSION_CLASSES': [
    # 默认不做权限限制
    'rest_framework.permissions.AllowAny',
    ],
    
class AllowAny(BasePermission):
    def has_permission(self, request, view):
        return True

"""    
DRF默认提供的些权限类:
    AllowAny:游客和登录用户有全权限
    IsAuthenticated:只有登录用户有全权限
    IsAdminUser:只有后台用户(admin用户)有全权限
    IsAuthenticatedOrReadOnly:游客有读权限,登录用户有全权限
"""
  1. 自定义权限类
    1. 继承BasePermission
    2. 重写has_permission方法
    3. 方法体
      1. 根据实际需求设置条件
      2. 返回True, 代表有权限
      3. 返回False, 代表无权限
# permissions.py
from rest_framework.permissions import BasePermission
# vip用户权限
class VipPermission(BasePermission):
    def has_permission(self, request, view):
        for group in request.user.groups.all():
            if group.name.lower() == 'vip':
                return True
        return False
  1. 局部配置权限类
# views.py
# 只有vip用户才能进行单查
class UserViewSet(ViewSet):
    # 局部配置权限类
    permission_classes = [permissions.VipPermission]

    def retrieve(self, request, *args, **kwargs):
        return APIResponse(results=
            'username': request.user.username,
            'email': request.user.email,
            'mobile': request.user.mobile
        )

频率组件

  1. 自定义频率组件

    1. 继承SimpleRateThrottle
    2. 设置 scope=‘xxx‘, xxx 对应的是在settings.py设置的频率 ‘xxx‘: ‘1/min‘
    3. 重写get_cache_key方法
    4. 方法体:
      1. 返回None, 不做限制
      2. 返回self.cache_format, 有频率限行
# throttles.py
from rest_framework.throttling import SimpleRateThrottle


# 自定义频率限制类: 按照手机号限行
class MobileRateThrottle(SimpleRateThrottle):
    scope = 'mobile'

    def get_cache_key(self, request, view):
        # 匿名用户和没有手机号的不做限制
        if not request.user.is_authenticated or not request.user.mobile:
            return None  # 反正None就是不做限制

        return self.cache_format % 
            'scope': self.scope,
            'ident': request.user.mobile
        
# settings.py
REST_FRAMEWORK = 
    # 频率类一般是局部配置, 但是频率调节在settings.py中配置
    'DEFAULT_THROTTLE_RATES': 
        'user': '5/min',
        'anon': '3/min',
        'mobile': '1/min'
    ,

自定义token的签发

  • 要实现多方式登录, 一定要自定义token的签发
class LoginModelSerializer(serializers.ModelSerializer):
    username = serializers.CharField(max_length=12, min_length=3)
    password = serializers.CharField(min_length=6)

    class Meta:
        model = models.User
        fields = ('username', 'password')

    # 全局钩子完成token签发
    def validate(self, attrs):
        # 1.获取user对象
        user = self._validate_user(attrs)
        # 2.获取payload
        payload = jwt_payload_handler(user)
        # 3.获取token
        token = jwt_encode_handler(payload)
        # 4.将user和token保存到serializer对象中, 以便在视图类中使用
        self.content = 
            'user': user,
            'token': token
        
        return attrs

    # 多方式登录
    def _validate_user(self, attrs):
        username = attrs.get('username')
        password = attrs.get('password')

        # 邮箱
        if re.match(r'.*@.*', username):
            user = models.User.objects.filter(email=username).first()
        # 手机号
        elif re.match(r'1[3-9][0-9]9$', username):
            user = models.User.objects.filter(mobile=username).first()
        # 用户名
        else:
            user = models.User.objects.filter(username=username).first()

        if not user or not user.check_password(password):
            raise serializers.ValidationError('msg': '用户名或密码错误')

        return user

drf08(代码片段)

目录三大认证流程认证组件权限组件频率组件自定义token的签发三大认证流程由于DRF中,所有的视图类都要直接和间接继承APIView类,也只有APIView类中才有dispatch方法,所以所有的请求都要经过三大认证,认证通过后执行相应请求的视... 查看详情

drf——认证(代码片段)

drf认证官网地址:https://www.django-rest-framework.org/api-guide/requests/1.drf的执行流程与源码剖析fromrest_framework.viewsimportAPIViewclassStudentView(APIView):defget(self,request,*args,**kwargs):pass说明:图片上的settings 查看详情

2.drf入门(代码片段)

drf介绍DjangoRESTframework(简称:DRF)是一个强大而灵活的WebAPI工具。遵循RESTFullAPI风格,功能完善,可快速开发API平台。官网文档:https://www.django-rest-framework.orgDjangoRESTframework最新版使用要求:Python(3.6、3.7、3.8、3.9、3.10)Django(2.2、3.0、3.1... 查看详情

drf路由(代码片段)

"在urls.py文件中按照如下步骤写,即可正确使用DRF的内置路由.from.viewsimportBookModel#1.导入我们的视图fromrest_framework.routersimportDefaultRouter#2.导入rest_framework内置的路由方法router=DefaultRouter()#3.首先,实例化一个DefaultRouter对象router 查看详情

drf缓存解决方案drf-extensions/redis(代码片段)

drf-extensions概述drf-extensions组件内部提供了DRF 的本地内存方式的缓存方式本地内存方式缓存在项目重启后则会消失官方点击这里  安装pip3installdrf-extensionsorfromgithubpip3installhttps://github.com/chibisov/drf-extensions/archive/maste 查看详情

19-djangorestframework-drf工程搭建(代码片段)

DRF工程搭建前言环境安装与配置安装DRF注册DRF应用DRF体验1.创建序列化器2.编写视图3.定义路由4.运行测试前言本篇来学习DRF工程搭建及体验环境安装与配置DRF需要以下依赖:Python(2.7,3.4,3.5,3.6,3.7)Django(1.11,2.0,2.1)DRF是以Django扩展... 查看详情

drf-分页(代码片段)

目录一、三种分页模式1PageNumberPagination2LimitOffsetPagination3CursorPagination二、继承APIView的视图类下写分页一、三种分页模式1PageNumberPaginationfromrest_framework.paginationimportPageNumberPagination,LimitOffsetPagination,Curs 查看详情

初识drf(代码片段)

....1.1创建django项目6.2添加rest_framework应用6.3体验drf完全简写代码的过程6.3.0创先子应用6.3.1.创建模型操作类6.3.1.1执行数据迁移6.3.2.创建序列化器6.3.3.编写视图6.3.4.定义路由6 查看详情

drf序列化(代码片段)

一、安装Django RESTframework框架使用命令:pipinstalldjangorestframework二、在setings里面注册INSTALLED_APPS=["rest_framework"]Serializers序列化组件 查看详情

drf分页器(代码片段)

drf分页器1.第一种分页:类似于django中的分页2.第二种分页:偏移分页3.第三种分页:加密分页(查询速度快)无法跳跃基本参数fromrest_framework.paginationimportPageNumberPagination,LimitOffsetPagination,CursorPaginationpage_size#每页显示的数量page_query_param=... 查看详情

drf分页(代码片段)

 restframework中提供三种分页:fromrest_framework.paginationimportPageNumberPagination,LimitOffsetPagination,CursorPagination 全局配置文件:REST_FRAMEWORK=‘PAGE_SIZE‘:21.分页,看第n页,每页显示n条数据例如:http://127.0.0. 查看详情

drf之分页器(代码片段)

一、简介:drf内置了三种分页器类,一般需要重写类继承默认的分页器类来定制属性的具体数值。二、PageNumberPagination  1、路径:rest_framework.pagination.PageNumberPagination。  2、重写类:classNewPageNumberPagination(PageNumberPagination):page... 查看详情

12.drf-节流(代码片段)

Djangorestframework源码分析(3)----节流添加节流自定义节流的方法限制60s内只能访问3次(1)API文件夹下面新建throttle.py,代码如下:#utils/throttle.pyfromrest_framework.throttlingimportBaseThrottleimporttimeVISIT_RECORD=#保存访问记录classVisitThrottl 查看详情

drf框架(代码片段)

DRF框架知识总览一、接口(api):什么是接口接口文档接口规范二、FBV=>CBV:Function|ClassBaseViewCBV的请求生命周期CBV比FBV的优势三、drf框架的基础试图类APIView:请求模块、解析模块、渲染模块、响应模块、异常模块四、drf核心组件... 查看详情

drf之jwt补充(代码片段)

DRF之JWT补充1.JWT控制用户登录后才能反问,匿名用户无法访问classQueryUserView(GenericViewSet,RetrieveModelMixin):"""查询接口"""queryset=User.objects.all()serializer_class=UserSerializerpk=None#thrott 查看详情

drf-路由和认证(代码片段)

drf-路由目录drf-路由1路由1.1路由router的使用1.2action的使用2认证2.1认证的写法2.2源码分析2.3认证组件的使用1路由针对视图集ViewSet,我们出来可以自己手动指明请求方式与执行函数间的对应关系,还可以使用Routers来快速实现路由... 查看详情

drf-解析器组件(代码片段)

DRF之解析器组件引入DjangoRestFramework帮助我们实现了处理application/json协议请求的数据,另外,我们也提到,如果不使用DRF,直接从request.body里面拿到原始的客户端请求的字节数据,经过decode,然后json反序列化之后,也可以得到一... 查看详情

drf概述(代码片段)

DRF概述一.REST1.什么是编程?数据结构和算法的结合2.什么是REST?回顾曾经做过的图书管理系统,我们是这样设计URL的:  127.0.0.1:9001/books/  127.0.0.1:9001/get_all_books/访问所有的数据127.0.0.1:9001/books/id/127.0.0.1:9001/books/id?method=get访问单... 查看详情