Tutorial · Laravel · API

Build a Rate-Limited Public API from Scratch in Laravel

Joy Dey July 17, 2026 8 min read Laravel API Backend Tutorial

When building a public-facing API, one of the most important considerations is preventing abuse. If an API is completely open without any restrictions, a single malicious user or a runaway script could flood your server with requests, causing it to crash or run up massive infrastructure bills.

In this tutorial, we will build a public API from scratch using Laravel and secure it against abuse by implementing rate limiting using Laravel's powerful built-in rate limiter.

Step 1: Setting Up the Laravel Project

Let's start by creating a new Laravel project. Open your terminal and run:

composer create-project laravel/laravel rate-limited-api
cd rate-limited-api

Next, let's create a simple model and migration for the data we want to expose through our API. For this example, let's assume we are building an API that serves a list of books.

php artisan make:model Book -m

In the generated migration file, define the schema for the books table:

public function up()
{
    Schema::create('books', function (Blueprint $table) {
        $table->id();
        $table->string('title');
        $table->string('author');
        $table->text('description');
        $table->timestamps();
    });
}

Run the migration to create the table:

php artisan migrate

Step 2: Creating the API Controller

Next, let's create a controller to handle the API requests.

php artisan make:controller Api/BookController

Open app/Http/Controllers/Api/BookController.php and add a method to return the list of books:

namespace App\Http\Controllers\Api;

use App\Http\Controllers\Controller;
use App\Models\Book;
use Illuminate\Http\Request;

class BookController extends Controller
{
    public function index()
    {
        $books = Book::all();
        
        return response()->json([
            'status' => 'success',
            'data' => $books
        ]);
    }
}

Step 3: Defining the API Route

Now we need to define the route for our API endpoint. Open routes/api.php and add the following:

use App\Http\Controllers\Api\BookController;
use Illuminate\Support\Facades\Route;

Route::get('/books', [BookController::class, 'index']);

Step 4: Implementing Rate Limiting

By default, Laravel includes a api middleware group in app/Http/Kernel.php which automatically applies a basic rate limit (usually 60 requests per minute). But let's define a custom, stricter rate limit for our public API.

Open app/Providers/RouteServiceProvider.php. In the configureRateLimiting method, you can define your custom rate limiter. Let's create a rate limiter called public-api that restricts users to 10 requests per minute based on their IP address:

use Illuminate\Cache\RateLimiting\Limit;
use Illuminate\Support\Facades\RateLimiter;

protected function configureRateLimiting()
{
    RateLimiter::for('public-api', function (Request $request) {
        return Limit::perMinute(10)->by($request->ip());
    });
}

Now, apply this rate limiter to our API route in routes/api.php by attaching the throttle middleware:

Route::middleware('throttle:public-api')->group(function () {
    Route::get('/books', [BookController::class, 'index']);
});

Step 5: Testing the Rate Limit

You can test the rate limit using tools like Postman, Insomnia, or simply via cURL in your terminal.

Make a GET request to /api/books. Notice the headers in the response:

  • X-RateLimit-Limit: 10
  • X-RateLimit-Remaining: 9

If you make more than 10 requests within a minute, Laravel will automatically return a 429 Too Many Requests HTTP response, preventing further access until the time window resets.

Conclusion

Rate limiting is a fundamental aspect of building robust public APIs. Laravel's built-in rate limiter makes it incredibly easy to define and apply complex rate limiting strategies with just a few lines of code, protecting your application from abuse and ensuring fair usage for all users.