NAME

App::Cerberus::Plugin::Throttle - Throttle request rates based on IP ranges

VERSION

version 0.11

DESCRIPTION

This plugin allows you to throttle (rate limit) requests per second, per minute, per hour, per day or per month. Different limits can apply to different network ranges, and to different events.

REQUEST PARAMS

Throttling information is returned when an IPv4 address is passed in:

curl http://host:port/?ip=64.233.160.1

Optionally, an event name can be included, which defaults to 'default'.

curl http://host:port/?ip=64.233.160.1;event=foo

CONFIGURATION

plugins:
  - Throttle:
        store:
            Memcached:
                namespace:  cerberus
                servers:
                    -       localhost:11211

        second_penalty:     5
        ranges:
            default:
                ips:        0.0.0.0/0
                limit:
                            - 20 per second
                            - 100 per minute

            google_bot:
                group_ips:  1
                limit:      10 per second
                ips:
                            - 64.233.160.0/19
                            - 66.102.0.0/20

            abusive:
                limit:      banned
                ips:
                            - 205.217.153.73
                            - 199.19.249.196

store

There are two store backends available: Memory and Memcached. The Memory backend should NEVER be used in production. It is for testing purposes only:

plugins:
    - Throttle:
        store:      Memory
        ranges:    ...

The Memcached backend uses Cache::Memcached::Fast and you can pass whatever options you would pass to new().

- Throttle:
      store:
          Memcached:
              namespace:  cerberus
              servers:
                  -       localhost:11211

ranges

The key for each range is its name, eg default, google_bot etc, which is returned by Cerberus.

ips

The ips parameter is compiled into a regex using Net::IP::Match::Regexp. If two ranges interesect, then the more specific range matches.

group_ips

If you want any IP address in a range to be considered the same user (eg all IPs from Google), then specify:

group_ips: 1

Otherwise each IP address will be treated separately.

limit

The limit parameter can be:

none

Impose no limits

banned

Never allow

MAX per PERIOD

For instance, 5 per second or 10 per minute. MAX can be any positive integer and PERIOD any of second, minute, hour, day or month.

If no IP is passed, or if the IP does not match any range, this plugin returns:

"throttle": {
    "sleep": 0
}

If a range is matched, but the limit is not exceeded, the plugin returns (eg):

"throttle": {
    "range": "google",
    "sleep": 0
}

If the limit has been exceeded, the plugin returns (eg):

"throttle": {
    "range":         "google",
    "reason":        "second",
    "sleep":         10,
    "request_count": 12
}

Or, if banned:

"throttle": {
    "range": "google",
    "sleep": -1,
    "reason": "banned"
}

events

If you want to use different limits per event, then the config should be as follows:

plugins:
  - Throttle:
    events:
        default:
            ranges:
                default:
                    ips:        0.0.0.0/0
                    limit:
                                - 20 per second
                                - 100 per minute
        my_event:
            ranges:
                default:
                    ips:        0.0.0.0/0
                    limit:      5 per second

second_penalty

The value for sleep reflects the number of seconds that the requesting user should wait until they try again. If the limit that has been exceeded is the number of request per second, this value will be 1.

If you want to impose a bigger penalty ("Woah, slow down cowboy!") you can specify a second_penalty. Note: this is advisory only. Only polite robots will respect this value.

AUTHOR

Clinton Gormley <drtech@cpan.org>

COPYRIGHT AND LICENSE

This software is copyright (c) 2014 by Clinton Gormley.

This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself.