Get "PHP 8 in a Nuthshell" (Now with PHP 8.4)
Amit Merchant

Amit Merchant

A blog on PHP, JavaScript, and more

Implementing SaaS Usage Limits in Laravel

If you’ve ever worked with SaaS models, you’d be familiar with the concept of usage limits. It’s the most important metric for any SaaS product.

The usage limit essentially lets you figure out how much a user can use your product for based on a plan they’ve subscribed to.

For instance, if you have a plan that allows a user to use 100 units of a product per month, you can set the usage limit to 100. And once the user has used 100 units, they can’t use the product anymore. To continue using the product, they’ll probably need to upgrade to a higher plan.

I recently came across a Laravel package that makes it pretty easy to implement usage limits in your Laravel application taking away the hassle of managing the usage limits yourself.

Laravel Usage Limiter

The Laravel Usage Limiter is a package that allows you to implement usage limits in your Laravel application easily. It can track, limit & restrict usages by setting them on your models (usually User model).

It comes with the following features:

  • Define usage limits you need for your app per plan
  • Set reset frequency for each of your limits
  • Attach usage limits to models (e.g. User model)
  • Consume and unconsume usage limits whenever a resource is created or deleted
  • Get usage report of a specific model (e.g. User model)
  • Check and determine if a model can consume more resources
  • Manually reset consumed usage limits of a model
  • Automatically reset consumed usage limits by setting reset frequencies such as every second, every minute, every hour, every day, every month, etc, and scheduling a built-in artisan command

Installation

To install the package, you can use Composer to add it to your project’s dependencies.

composer require nabilhassen/laravel-usage-limiter

After installing the package, you need to publish the package’s configuration file using the following command.

php artisan vendor:publish --provider="NabilHassen\LaravelUsageLimiter\ServiceProvider"

This will publish the configuration file to the config/limit.php file in your Laravel project. This is where you can configure table names, relationships, etc.

And finally, run migrations to create the database tables.

php artisan migrate

This will create two new tables in your database: limits and model_has_limits.

Usage

Now, without going too deep, I’ll show you how this package works with an example. You can check its repository out for more details.

So, let’s say you have a User model that represents a user in your application. You want to limit the user’s usage of a resource, such as a product, to a certain amount. For example, a user can only use 100 units of a product per month for a certain plan. Let’s say the plan is called basic with an amount of 100 units.

You need to create a limit for this plan.

You can create it like this.

$limit = Limit::create([
    'name' => 'products',
    'allowed_amount' => 100,
    'plan' => 'basic',
    'reset_frequency' => 'every month',
]);

This will create a new limit with the name products, allowed amount of 100, plan basic, and reset frequency of every month which will reset the limit every month.

You can also create it using a command.

php artisan limit:create products 100 basic

This will create a limit with the given name, allowed amount, plan, and reset frequency in the limits table.

Next, you need to add the HasLimits trait to your User model for which you want to limit usages.

use NabilHassen\LaravelUsageLimiter\Traits\HasLimits;

class User extends Authenticable
{
    use HasLimits;
}

Then, you can set the usage limit for a model by passing the name of the limit and the plan.

$user = User::find(1);

$user->setLimit(limit: 'products', plan: 'basic');

Once the user’s limit is set, you can start consuming the limit by calling the useLimit method.

// This will consume 1 unit of the limit and
// update the consumed amount in the database
$user->useLimit(limit: 'products', plan: 'basic');

// This will consume 10 units of the limit
$user->useLimit(limit: 'products', plan: 'basic', 10);

You can check the remaining limit for the user like so.

// This will return 90 if the plan limit is 100
// and the user has consumed 10 units
$user->remainingLimit(limit: 'products', plan: 'basic'); // 90

If you just want to check if the user has enough limit, you can do it like so.

$user->hasEnoughLimit(limit: 'products', plan: 'basic'); // true

You can reset the limit for a user by calling the resetLimit method.

$user->resetLimit(limit: 'products', plan: 'basic');

You can get the report of the limit for a user like so.

$user->limitUsageReport(limit: 'products', plan: 'basic');

/*
array:1 [▼ // routes/web.php:34
  "products" => array:3 [▼
    "allowed_amount" => "100.0000"
    "used_amount" => "10.0000"
    "remaining_amount" => "90.0000"
  ]
]
*/

There’s even a handy Blade directive to check if the user has enough limit.


@limit($user, 'products', 'basic')
    // user has enough limits left
@else
    // user has NO enough limits left
@endlimit

In closing

And that was a high-level overview of how to use this package to implement usage limits in your Laravel application. You can also do advanced things like scheduling the reset of the limit using a command, extending the package, playing around with caching, and more.

→ Learn more about the package: Laravel Usage Limiter

Learn the fundamentals of PHP 8 (including 8.1, 8.2, 8.3, and 8.4), the latest version of PHP, and how to use it today with my new book PHP 8 in a Nutshell. It's a no-fluff and easy-to-digest guide to the latest features and nitty-gritty details of PHP 8. So, if you're looking for a quick and easy way to PHP 8, this is the book for you.

Like this article?

Buy me a coffee

👋 Hi there! I'm Amit. I write articles about all things web development. You can become a sponsor on my blog to help me continue my writing journey and get your brand in front of thousands of eyes.

Comments?