class RateLimiter(base.Object):
- def handle_request(self, request, handler, minutes, limit, **kwargs):
- return RateLimiterRequest(self.backend, request, handler,
- minutes=minutes, limit=limit, **kwargs)
+ def __call__(self, *args, **kwargs):
+ """
+ Launch a new request
+ """
+ return RateLimiterRequest(self.backend, *args, **kwargs)
async def cleanup(backend):
"""
class RateLimiterRequest(base.Object):
- def init(self, request, handler, minutes, limit, key=None):
+ def init(self, request, handler, *, minutes, limit, key=None):
self.request = request
self.handler = handler
await self.render("login.html", username=username, failed=failed)
- @base.ratelimit(requests=10, minutes=5)
+ @base.ratelimit(limit=10, minutes=5)
async def post(self):
# Fetch credentials
username = self.get_argument("username")
"""
A decorator class which limits how often a function can be called
"""
- def __init__(self, *, minutes, requests):
- self.minutes = minutes
- self.requests = requests
+ def __init__(self, **kwargs):
+ self.kwargs = kwargs
def __call__(self, method):
@functools.wraps(method)
async def wrapper(handler, *args, **kwargs):
# Pass the request to the rate limiter and get a request object
- req = handler.backend.ratelimiter.handle_request(handler.request,
- handler, minutes=self.minutes, limit=self.requests)
+ req = handler.backend.ratelimiter(handler.request, handler, **self.kwargs)
# If the rate limit has been reached, we won't allow
# processing the request and therefore send HTTP error code 429.