---
title: "Named limiter profiles — HTTP Client Rate Limits for Laravel | Roundly"
description: "Define reusable limits once in config and reference them by name — Http::rateLimit('github') — with every option available."
url: https://roundly-consulting.com/open-source/docs/http-client-rate-limits-for-laravel/named-profiles
language: en
---

[All packages](https://roundly-consulting.com/open-source.md)

[HTTP Client Rate Limits for Laravel](https://roundly-consulting.com/open-source/docs/http-client-rate-limits-for-laravel.md)

# Named limiter profiles

Define reusable limits once in config/http-client-rate-limits.php and reference them by name from anywhere:

```php
// config/http-client-rate-limits.php
'limiters' => [
    'github' => ['rate' => 5, 'per' => 'second'],
    'billing' => ['rate' => 100, 'per' => 'minute', 'by' => 'tenant-1', 'jitter' => 50],
],
```

```php
use RoundlyConsulting\HttpClientRateLimits\Facades\RateLimits;

Http::rateLimit('github')->get('https://api.github.com/user');

// Re-key a profile per owner at the call site:
Http::rateLimit('github', by: 'acct-1')->get('https://api.github.com/user');

// The same profile outside the HTTP client:
$limit = RateLimits::profile('github');
$limit->remaining();
```

Referencing a name that isn’t defined throws UnknownLimiterProfileException.

Without by, a profile is keyed by its own name, so each profile keeps its own budget and its own server backoff — one API asking you to slow down never holds up the others. Give profiles the same by to make them share one budget.

## Profile keys

Each profile array accepts rate and per, plus the optional by, trim, max\_wait, jitter and adaptive keys. A key that is not set — omitted, null or blank ('', whitespace) — falls back to these defaults:

| Key | Default | Purpose |
| --- | --- | --- |
| `rate` | 1 | Requests allowed in the window. |
| `per` | minute | Window: second, minute, hour or day. |
| `by` | null (the profile name) | Owner key the budget is tracked under. Profiles with the same by share one budget. |
| `trim` | false | Drop the owner’s hits older than the window after each allowed request. |
| `max_wait` | null | Max wait in ms; a longer wait throws RateLimitExceededException. |
| `jitter` | 0 | Up to this many ms of random extra wait — never shortens a wait. |
| `adaptive` | false | Self-tune from Retry-After / X-RateLimit-\* response headers. |

A profile using every key:

```php
'limiters' => [
    'openai' => [
        'rate' => 60,          // requests allowed in the window
        'per' => 'minute',     // second | minute | hour | day
        'by' => 'openai',      // owner key
        'trim' => true,        // drop hits older than the window after each request
        'max_wait' => 10_000,  // ms: throw RateLimitExceededException above this wait
        'jitter' => 100,       // ms: up to this much random extra wait
        'adaptive' => true,    // honour Retry-After / X-RateLimit-* response headers
    ],
],
```

## Strict values

Every profile value is read strictly when the profile is resolved, never guessed at:

- rate, max\_wait and jitter take an integer or an integer string ('5'); 'five', '5.5' or '1e3' throws InvalidConfigurationException, and so does a negative max\_wait or jitter. A rate below 1 throws InvalidLimitException.
- per takes second, minute, hour or day (exact) or a Timespan; a typo such as minutes, or an unsupported week, throws InvalidTimespanException.
- by takes a string; a non-string throws InvalidConfigurationException.
- trim and adaptive take true/false, 1/0, on/off or yes/no; anything else throws InvalidConfigurationException.

Every error names the full key, e.g. http-client-rate-limits.limiters.github.adaptive. A key that is not set uses its default from the table above — so a blank max\_wait means no ceiling, never a 0 ms fail-fast one.

## Show your open-source love

This package is free and MIT-licensed. If it saves you time, a one-off donation or a Patreon membership keeps it maintained, tested and documented.

[More ways to support, including crypto](https://roundly-consulting.com/support-us.md)

By donating, you agree to our [donation terms](https://roundly-consulting.com/donation-terms.md).

[Support our open source work (opens in a new tab)](https://donate.stripe.com/dRmeVe8FX5PF1Qd9pXcEw00) [Join us on Patreon (opens in a new tab)](https://www.patreon.com/cw/roundly)

## Want this built into your product?

We integrate our packages into custom Laravel and AI builds. Tell us what you're working on and we'll reply within 48 hours.

[Get a quote in 48 hours](https://roundly-consulting.com/contact.md) [Browse all packages](https://roundly-consulting.com/open-source/docs/http-client-rate-limits-for-laravel.md)
