Skip to content

Throttle requests to your application based on users IP address.

License

Notifications You must be signed in to change notification settings

MadMikeyB/throttleable

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

15 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Laravel Throttleable

Packagist Packagist

Throttle requests to your application based on users IP address.

  • Set a threshold on how many requests an IP address can make.
  • Throttles expire after a configurable period of time.
  • Throttles are unique per IP address.
  • Configurable through config/throttleable.php

Installation

Pull in the package using Composer

composer require madmikeyb/throttleable

Note: If you are using Laravel 5.5, the next steps are unnecessary. Laravel Throttleable supports Laravel Package Discovery.

Include the service provider within app/config/app.php.

'providers' => [
    ...
    MadMikeyB\Throttleable\Providers\ThrottleableServiceProvider::class,
],

Migrations

You must publish the migration by running the following command:

php artisan vendor:publish --provider="MadMikeyB\Throttleable\Providers\ThrottleableServiceProvider" --tag="migrations" && php artisan migrate

Configuration

Throttleable supports optional configuration.

You can publish the config file with:

php artisan vendor:publish --provider="MadMikeyB\Throttleable\Providers\ThrottleableServiceProvider" --tag="config"

When published, the config/throttleable.php config file contains:

<?php

return [
    /**
     * Number of attempts permitted to a single
     * IP address before being throttled.
     */
    'attempt_limit' => 10,
    
    /**
     * The datetime metric to use for expirations
     * Available options are hour, day or week.
     */
    'expiry_metric' => 'week',

    /**
     * The number of hours, days or weeks to
     * keep a throttle valid for.
     */
    'expiry_timelimit' => 1
];

These are merely the default values and can be overriden on a case-by-case basis if needed.

Sample Usage

Simply import the Throttle Model in your controller.

<?php
namespace App\Http\Controllers;

use MadMikeyB\Throttleable\Models\Throttle;

Then, on whichever method you'd like to throttle, new up a Throttle instance. The minimum parameters required by this class is an instance of Illuminate\Http\Request.

The check() method of Throttle returns a boolean, which indicates whether the IP address has been throttled or not.

public function create(Request $request) 
{
    $throttle = new Throttle($request->instance());
    
    if (!$throttle->check()) {
       alert()->error('Sorry, you have made too many requests. Please try again later.');
       return back();
    }
}

NB. the alert() helper is provided by uxweb/sweet-alert and is not included in this package.

Full Example

<?php
namespace App\Http\Controllers;

use App\Comment;
use MadMikeyB\Throttleable\Models\Throttle;

class CommentsController 
{
    public function store(Request $request) 
    {
        $throttle = new Throttle($request->instance());
        
        if (!$throttle->check()) {
           alert()->error('Sorry, you have made too many requests. Please try again later.');
           return back();
        }

        // save comment here
        Comment::create($request->all());
        alert()->success('Comment Created!');
        return back();
    }
}

Overriding Configuration on a case-by-case basis

In some cases you may want to override the default attempt and time limits which are set in the configuration file. For example, a user creating a comment may not be throttled as quickly as someone trying to log into an admin control panel.

The second and third arguments to the constructor of the Throttle model are the attempt_limit and the expiry_weeks configuration variables respectively.

If you need to override the defaults set in config/throttleable.php, you would do so as follows:

public function store(Request $request) 
{
    $attemptLimit = 10000;
    $expiryWeeks = 52;

    $throttle = new Throttle($request->instance(), $attemptLimit, $expiryWeeks);
    
    if (!$throttle->check()) {
       alert()->error('Sorry, you have made too many requests. Please try again later.');
       return back();
    }

    // save comment here
    Comment::create($request->all());
    alert()->success('Comment Created!');
    return back();
}

License

The MIT License (MIT). Please see License File for more information.