Django Rest framework的限流实现流程

一 什么是throttle

节流也相似于权限,它用来决定一个请求是否被受权。节流表示着一种临时的状态,经常用来控制客户端对一个
API的请求速率。例如,你能够经过限流来限制一个用户在每分钟对一个API的最多访问次数为60次,天天的访问次数为1000次。
 python

二 Django REST framework是如何实现throttle的

  1. 在Django REST framework中主要是经过throttling.py文件里面的几个类来实现限流功能的。django

  2. 在整个流程上是在dispatch中的调用的initial方法中的self.check_throttles(request)调用到throttle类中的方法api

  3. throttle策略的配置:
    全局配置settings.py
REST_FRAMEWORK = {
    'DEFAULT_THROTTLE_CLASSES': (  # 定义限流类
        'rest_framework.throttling.AnonRateThrottle',
        'rest_framework.throttling.UserRateThrottle'
    ),
    'DEFAULT_THROTTLE_RATES': {   # 定义限流速率,支持秒、分、时、天的限制
        'anon': '100/day',
        'user': '1000/day'
    }
}
  1. 把限流策略设置在视图函数上
    CBV
from rest_framework.response import Response
from rest_framework.throttling import UserRateThrottle
from rest_framework.views import APIView
class ExampleView(APIView):
    throttle_classes = (UserRateThrottle,)
    def get(self, request, format=None):
        content = {
            'status': 'request was permitted'
        }
        return Response(content)

FBVruby

@api_view(['GET'])
@throttle_classes([UserRateThrottle])
def example_view(request, format=None):
    content = {
        'status': 'request was permitted'
    }
    return Response(content)

 

三 Django REST framework中throttle源码流程

  1. 调用check_throttles方法,在这个方法中会遍历经过self.get_throttles()获取到的限流对象列表,默认列表里面是空的。也就是说默认不会有限流的策略。markdown

  2. 在视图函数里面配置参数,让其应用上限流策略。咱们这里以UserRateThrottle这个限流方法为例。(配置如第二节中的settings.py配置和FBV配置),在这里继续第二步的操做,执行UserRateThrottle对象的allow_request方法。
    因为UserRateThrottle这个类自己没有allow_request方法,因此在其父类SimpleRateThrottle中找这个方法.ide

  3. 执行allow_request方法,会首先判断是否认义了self.rate。根据self.rate执行,最终回去查找self.scope属性,并且这个属性是必须的。函数

  4. 在UserRateThrottle中查找到定义的scope="user", 接着执行self.key语句。这条语句最终调用了UserRateThrottle里面的get_cache_key方法。
    此例中咱们没有配置authenticate,全部会执行get_cache_key里面的get_indet方法,并最终返回了scope和ident被self.key接收(返回格式:throttle_user_127.0.0.1)。post

  5. 返回self.key以后继续执行self.history,self.history会返回客户端的访问记录列表,并根据rate的配置去判断是不是要pop某一条访问记录。并最终根据列表长度和容许的长度作对比,判断客户端当前是否具备访问权限。spa

  6. 若最终check_throttles返回True,则继续执行dispatch。dispatch以后的操做请参考以前写的django rest framework流程。若是返回False,则会继续执行self.throttled(request, throttle.wait())。3d

  7. 执行父类SimpleRateThrottle里面的wait方法。这个方法主要用来向客户端返回还须要多少时间能够继续访问的提示。

相关文章
相关标签/搜索