Throttling - Django REST framework

节流-Django REST框架

throttling.py

节流

http/1.1 420增强你的冷静

Twitter API速率限制响应

节流类似于权限,因为它决定是否应该授权请求。节流阀表示临时状态,用于控制客户端向API发出请求的速率。

与权限一样,可以使用多个节流阀。对于未经身份验证的请求,您的API可能有一个限制性节流阀,对于经过身份验证的请求,您的API可能有一个限制较

另一个您可能希望使用多个节流阀的场景是,如果您需要对API的不同部分施加不同的约束,因为某些服务是特别资源密集型的。

如果您想要强制执行突发节流率和持续节流率,也可以使用多个节流器。例如,您可能希望将用户限制为每分钟最多60个请求,以及每天1000个请求。

节流阀不一定只指限速请求.例如,存储服务可能还需要节流带宽,而付费数据服务可能希望限制访问的记录数量。

节流是如何确定的

与权限和身份验证一样,REST框架中的节流总是定义为类列表。

在运行视图的主体之前,检查列表中的每个节流阀。如果油门检查失败,则exceptions.Throttled将引发异常,并且视图的主体将不会运行。

设置节流策略

默认节流策略可以全局设置,使用DEFAULT_THROTTLE_CLASSESDEFAULT_THROTTLE_RATES设置。例如。

REST_FRAMEWORK = {
    'DEFAULT_THROTTLE_CLASSES': [
        'rest_framework.throttling.AnonRateThrottle',
        'rest_framework.throttling.UserRateThrottle'
    ],
    'DEFAULT_THROTTLE_RATES': {
        'anon': '100/day',
        'user': '1000/day'
    }
}

中使用的费率说明。DEFAULT_THROTTLE_RATES可能包括second, minute, hourday作为节流期。

还可以使用APIView基于类的视图。

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)

或者,如果您使用的是@api_view具有基于功能的视图的装饰器。

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

如何识别客户

这个X-Forwarded-Forhttp标头和REMOTE_ADDRWSGI变量用于唯一标识用于节流的客户端IP地址。如果X-Forwarded-For标头将被使用,否则将使用REMOTE_ADDR将使用来自WSGI环境的变量。

如果需要严格标识唯一的客户端IP地址,则首先需要通过设置NUM_PROXIES背景。此设置应为零或更多的整数。如果设置为非零,则客户端ip将标识为X-Forwarded-For标头,一旦任何应用程序代理IP地址第一次被排除。如果设置为零,则REMOTE_ADDR值将始终用作标识IP地址。

重要的是要理解,如果您配置NUM_PROXIES设置,则所有客户端后面都有一个唯一的纳特网关将被视为单个客户端。

进一步说明X-Forwarded-For标头工作,并且标识远程客户端ip可以是在这里发现的.

设置缓存

REST框架提供的节流类使用Django的缓存后端。你应该确保你已经设置了适当的缓存设置...的默认值LocMemCache后端应该可以用于简单的设置。见Django‘s缓存文档更多细节。

如果您需要使用'default',您可以通过创建自定义节流类并设置cache属性。例如:

from django.core.cache import caches

class CustomAnonRateThrottle(AnonRateThrottle):
    cache = caches['alternate']

您还需要记住在'DEFAULT_THROTTLE_CLASSES'设置键,或使用throttle_classes视图属性


API参考

AnonRateThrottle

这个AnonRateThrottle只会节流未经认证的用户。传入请求的IP地址被用来生成一个唯一的键来控制。

允许的请求率是从以下之一(按优先顺序)确定的。

  • 这个rate属性,可以通过重写AnonRateThrottle并设置财产。
  • 这个DEFAULT_THROTTLE_RATES['anon']背景。

AnonRateThrottle如果要限制来自未知来源的请求的速率,则适用。

UserRateThrottle

这个UserRateThrottle通过API将用户限制到给定的请求速率。用户id用于生成一个唯一的键来控制油门。未经身份验证的请求将退回到使用传入请求的IP地址来生成一个唯一的键来控制。

允许的请求率是从以下之一(按优先顺序)确定的。

  • 这个rate属性,可以通过重写UserRateThrottle并设置财产。
  • 这个DEFAULT_THROTTLE_RATES['user']背景。

一个API可能有多个UserRateThrottles同时就位。若要这样做,请重写UserRateThrottle并为每个类设置唯一的“作用域”。

例如,可以使用以下类实现多个用户节流率.

class BurstRateThrottle(UserRateThrottle):
    scope = 'burst'

class SustainedRateThrottle(UserRateThrottle):
    scope = 'sustained'

.和下面的设置

REST_FRAMEWORK = {
    'DEFAULT_THROTTLE_CLASSES': [
        'example.throttles.BurstRateThrottle',
        'example.throttles.SustainedRateThrottle'
    ],
    'DEFAULT_THROTTLE_RATES': {
        'burst': '60/min',
        'sustained': '1000/day'
    }
}

UserRateThrottle如果您希望对每个用户进行简单的全局速率限制,则是合适的。

ScopedRateThrottle

这个ScopedRateThrottle类可用于限制对API特定部分的访问。只有当正在访问的视图包括.throttle_scope财产。然后,通过将请求的“范围”与唯一的用户id或IP地址连接起来,形成唯一的节流键。

允许的请求速率由DEFAULT_THROTTLE_RATES使用请求“作用域”中的键设置。

例如,给定以下视图..。

class ContactListView(APIView):
    throttle_scope = 'contacts'
    ...

class ContactDetailView(APIView):
    throttle_scope = 'contacts'
    ...

class UploadView(APIView):
    throttle_scope = 'uploads'
    ...

.和下面的设置

REST_FRAMEWORK = {
    'DEFAULT_THROTTLE_CLASSES': [
        'rest_framework.throttling.ScopedRateThrottle',
    ],
    'DEFAULT_THROTTLE_RATES': {
        'contacts': '1000/day',
        'uploads': '20/day'
    }
}

用户请求ContactListViewContactDetailView将被限制在每天1000次的请求范围内。用户请求UploadView将被限制为每天20次请求。


定制节流阀

若要创建自定义节流阀,请重写BaseThrottle和实施.allow_request(self, request, view)...方法应该返回True如果请求被允许,以及False不然的话。

也可以选择覆盖.wait()方法。如果实施,.wait()应该返回建议等待的秒数,然后再尝试下一个请求,或None...这个.wait()方法只在下列情况下才会调用。.allow_request()以前已经回来了False.

如果.wait()方法,并对请求进行节流,然后将Retry-After报头将包括在响应中。

以下是一个速度节流阀的例子,它将随机节流1每10个请求。

import random

class RandomRateThrottle(throttling.BaseThrottle):
    def allow_request(self, request, view):
        return random.randint(1, 10) != 1
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

QMQ2021

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值