CGI::Application::Plugin::Throttle - Rate-Limiting for CGI::Application-based applications, using Redis for persistence.
use CGI::Application::Plugin::Throttle; # Your application sub setup { ... # Create a redis handle my $redis = Redis->new(); # Configure throttling $self->throttle()->configure( redis => $redis, prefix => "REDIS:KEY:PREFIX", limit => 100, period => 60, exceeded => "slow_down_champ" );
This module allows you to enforce a throttle on incoming requests to your application, based upon the remote IP address.
This module stores a count of accesses in a Redis key-store, and once hits from a particular source exceed the specified threshold the user will be redirected to the run-mode you've specified.
Users who share IP addresses, because they are behind a common-gateway for example, will all suffer if the threshold is too low. We attempt to mitigate this by building the key using a combination of the remote IP address, and the remote user-agent.
This module will apply to all run-modes, because it seems likely that this is the most common case. If you have a preference for some modes to be excluded please do contact the author.
Force the throttle method into the caller's namespace, and configure the prerun hook which is used by CGI::Application.
throttle
This method is used internally, and not expected to be invoked externally.
The defaults are setup here, although they can be overridden in the "configure" method.
Gain access to an instance of this class. This is the method by which you can call methods on this plugin from your CGI::Application derived-class.
Build and return the Redis key to use for this particular remote request.
The key is built from the prefix string set in "configure" method, along with:
prefix
The remote IP address of the client.
The remote HTTP Basic-Auth username of the client.
The remote User-Agent.
Return the number of times the remote client has hit a run mode, along with the maximum allowed visits:
sub your_run_mode { my ($self) = (@_); my( $count, $max ) = $self->throttle()->count(); return( "$count visits seen - maximum is $max." ); }
This method is invoked by CGI::Application, as a hook.
The method is responsible for determining whether the remote client which triggered the current request has exceeded their request threshold.
If the client has made too many requests their intended run-mode will be changed to to redirect them.
This method is what the user will invoke to configure the throttle-limits.
It is expected that within the users CGI::Application "setup" in CGI::Application method there will be code similar to this:
sub setup { my $self = shift; my $r = Redis->new(); $self->throttle()->configure( redis => $r, # .. other options here ) }
The arguments hash contains the following known keys:
redis
A Redis handle object.
limit
The maximum number of requests that the remote client may make, in the given period of time.
period
The period of time which requests are summed for. The period is specified in seconds and if more than limit requests are sent then the client will be redirected.
This module uses Redis to store the counts of client requests. Redis is a key-value store, and each key used by this module is given a prefix to avoid collisions. You may specify your prefix here.
The prefix will default to the name of your application class if it isn't set explicitly, which should avoid collisions if you're running multiple applications on the same host.
exceeded
The run_mode to redirect the client to, when their request-count has exceeded the specified limit.
run_mode
Steve Kemp <steve@steve.org.uk>
Copyright (C) 2014 Steve Kemp <steve@steve.org.uk>.
This library is free software. You can modify and or distribute it under the same terms as Perl itself.
To install CGI::Application::Plugin::Throttle, copy and paste the appropriate command in to your terminal.
cpanm
cpanm CGI::Application::Plugin::Throttle
CPAN shell
perl -MCPAN -e shell install CGI::Application::Plugin::Throttle
For more information on module installation, please visit the detailed CPAN module installation guide.