Getting Started

Learn how to install and configure Universal Rate Limiter in your project

Installation

Install the package using your preferred package manager:

npm install universal-rate-limiter

# or with pnpm
pnpm add universal-rate-limiter

# or with yarn
yarn add universal-rate-limiter

# or with bun
bun add universal-rate-limiter

Basic Usage

Create a rate limiter instance and check if a request should be allowed:

basic-example.ts
1import { createRateLimiter, MemoryStorage } from 'universal-rate-limiter';
2
3// Create a limiter that allows 10 requests per minute
4const limiter = createRateLimiter({
5  key: 'api-requests',
6  max: 10,
7  window: '1m',
8  storage: new MemoryStorage()
9});
10
11// Check if request should be allowed
12const result = await limiter.check();
13
14if (result.allowed) {
15  console.log(`Request allowed. ${result.remaining} requests remaining.`);
16  // Process the request
17} else {
18  console.log(`Rate limited. Retry after ${result.retryAfter}ms`);
19  // Return 429 Too Many Requests
20}

Express Middleware

Protect your Express routes with the built-in middleware:

express-example.ts
1import express from 'express';
2import { rateLimitExpress } from 'universal-rate-limiter';
3
4const app = express();
5
6// Apply rate limiting to all routes
7app.use(rateLimitExpress({
8  key: 'api-limit',
9  max: 100,
10  window: '15m'
11}));
12
13// Or apply to specific routes
14app.get('/api/data',
15  rateLimitExpress({
16    key: (req) => `user-${req.ip}`,
17    max: 10,
18    window: '1m'
19  }),
20  (req, res) => {
21    res.json({ data: 'your data' });
22  }
23);

Next.js Edge Middleware

For Next.js 16+, use proxy.ts:

proxy.ts (Next.js 16+)
1import { rateLimitEdge } from 'universal-rate-limiter';
2
3export default rateLimitEdge({
4  key: (request) => request.ip ?? 'anonymous',
5  max: 50,
6  window: '1m',
7  onRateLimit: (request) => {
8    return new Response('Too many requests', {
9      status: 429,
10      headers: { 'Retry-After': '60' }
11    });
12  }
13});
14
15export const config = {
16  matcher: '/api/:path*',
17};

For Next.js 12-15, use middleware.ts:

middleware.ts (Next.js 12-15)
1import { NextResponse } from 'next/server';
2import type { NextRequest } from 'next/server';
3import { createRateLimiter, MemoryStorage } from 'universal-rate-limiter';
4
5const limiter = createRateLimiter({
6  key: (req: NextRequest) => req.ip ?? 'anonymous',
7  max: 50,
8  window: '1m',
9  storage: new MemoryStorage()
10});
11
12export async function middleware(request: NextRequest) {
13  const result = await limiter.check();
14
15  if (!result.allowed) {
16    return new NextResponse('Too Many Requests', {
17      status: 429,
18      headers: { 'Retry-After': '60' }
19    });
20  }
21
22  return NextResponse.next();
23}
24
25export const config = {
26  matcher: '/api/:path*',
27};

React Hook

Limit user actions on the client side:

MyComponent.tsx
1'use client';
2
3import { useRateLimit } from 'universal-rate-limiter';
4
5export function MyComponent() {
6  const { allowed, remaining, attempt } = useRateLimit('button-click', {
7    max: 3,
8    window: '1m'
9  });
10
11  const handleClick = async () => {
12    if (!allowed) {
13      alert('Too many clicks! Please wait.');
14      return;
15    }
16
17    await attempt();
18    // Perform action
19    console.log(`Action performed. ${remaining} remaining.`);
20  };
21
22  return (
23    <div>
24      <button onClick={handleClick} disabled={!allowed}>
25        Click Me ({remaining} left)
26      </button>
27    </div>
28  );
29}

Configuration Options

key

A unique identifier for the rate limit. Can be a string or a function that returns a string.

// Static key
key: 'api-requests'

// Dynamic key
key: (req) => `user-${req.userId}`

max

Maximum number of requests allowed within the time window.

max: 10  // Allow 10 requests

window

Time window for the rate limit. Supports human-readable formats or milliseconds.

window: '1m'    // 1 minute
window: '10s'   // 10 seconds
window: '1h'    // 1 hour
window: '1d'    // 1 day
window: 60000   // 60 seconds in milliseconds

storage

Storage adapter for persisting rate limit data. Defaults to MemoryStorage.

// Memory storage (default, lost on restart)
storage: new MemoryStorage()

// LocalStorage (browser only)
storage: new LocalStorageAdapter()

Next Steps