#37288: Add first-class rate limiting support for Django views
-------------------------------------+-------------------------------------
Reporter: Bader Eddine | Type: New
Benhirt | feature
Status: new | Component: HTTP
| handling
Version: 6.1 | Severity: Normal
Keywords: rate-limiting | Triage Stage:
security http views middleware | Unreviewed
cache |
Has patch: 0 | Needs documentation: 0
Needs tests: 0 | Patch needs improvement: 0
Easy pickings: 0 | UI/UX: 0
-------------------------------------+-------------------------------------
Django currently doesn't provide a built-in general-purpose mechanism for
rate limiting HTTP views.
Applications that need to protect endpoints against excessive requests
currently rely on third-party packages, custom middleware, reverse
proxies, or framework-specific solutions such as Django REST Framework
throttling.
I propose adding a small, framework-level rate limiting abstraction to
Django that can be used by regular function-based and class-based views.
A possible API could look like:
{{{
@rate_limit("api")
def index(request):
...
@rate_limit("api", methods={"POST", "PUT"})
def edit(request):
...
@rate_limit("exports", tokens=5)
def export(request):
...
Rate limit policies could be defined centrally in settings:
RATE_LIMITS = {
"api": {
"rate": "100/m",
"key": "ip",
},
"exports": {
"rate": "10/h",
"key": "user",
},
}
}}}
When a request exceeds its configured limit, Django could return an HTTP
429 Too Many Requests response and optionally include a Retry-After
header.
The implementation should ideally support:
function-based views and class-based views.
- authenticated-user and IP-based keys.
- custom callable keys.
- HTTP-method-specific limits.
- multiple rate limits on the same view.
- configurable request/token cost.
- Django's cache abstraction as a storage backend.
- synchronous and asynchronous views.
- 429 Too Many Requests and Retry-After.
- safe and clearly documented concurrency semantics.
There is already ticket #21289 concerning login rate limiting in
contrib.auth, but this proposal would provide a more general primitive for
Django HTTP views rather than being specific to authentication.
Similar declarative approaches now exist in other frameworks. For example,
Symfony 8.1 introduced a controller-level #[RateLimit] attribute. This
proposal would not aim to reproduce Symfony's API, but rather explore a
Django-native equivalent.
An important design question is whether this belongs in Django core or
should remain a third-party package. If considered suitable for core, I
would be interested in working on the implementation.
--
Ticket URL: <
https://code.djangoproject.com/ticket/37288>
Django <
https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.