UNPKG

express-limiter-pro

Version:

A TypeScript library for safe display and sanitization to prevent XSS attacks.

371 lines (262 loc) โ€ข 9.43 kB
# express-limiter-pro A comprehensive TypeScript library for Express.js applications that provides advanced rate limiting, authentication security, and configuration management. Protect your APIs from brute force attacks, DDoS attempts, and unauthorized access with intelligent rate limiting rules and dynamic configuration. ## Features - ๐Ÿ›ก๏ธ **Multi-tier Rate Limiting** - Different limits for API, authentication, and sensitive operations - ๐Ÿ” **2FA Protection** - Special rate limiting for two-factor authentication endpoints - โšก **High Performance** - Built with TypeScript and optimized for production - ๐ŸŽฏ **Intelligent Detection** - Header-based and path-based endpoint recognition - ๐Ÿ”ง **Dynamic Configuration** - Event-driven configuration management with hot reloading - ๐Ÿ“Š **Full TypeScript Support** - Complete type definitions and IntelliSense support - ๐Ÿงช **Battle Tested** - 80%+ test coverage with comprehensive test suite ## Table of Contents - [Installation](#installation) - [Quick Start](#quick-start) - [API Reference](#api-reference) - [Configuration](#configuration) - [Rate Limiting Rules](#rate-limiting-rules) - [Examples](#examples) - [Error Handling](#error-handling) - [TypeScript Support](#typescript-support) - [Contributing](#contributing) - [License](#license) ## Installation ```bash # Using npm npm install express-limiter-pro # Using yarn yarn add express-limiter-pro # Using pnpm pnpm add express-limiter-pro ``` ### Peer Dependencies This package requires Express.js as a peer dependency: ```bash npm install express ``` ## Quick Start ```typescript import express from 'express'; import { configureRateLimits, configManager, ConfigSource } from 'express-limiter-pro'; const app = express(); // Set up configuration source const configSource: ConfigSource = async () => ({ accessTokenSecret: process.env.ACCESS_TOKEN_SECRET || 'default-secret', isDevelopment: process.env.NODE_ENV === 'development' }); configManager.setConfigSource(configSource); // Configure rate limiting configureRateLimits(app); // Load configuration await configManager.loadConfig(); app.listen(3000); ``` ## API Reference ### `configureRateLimits(app: Application): void` Configures rate limiting middleware for an Express application with predefined rules for different endpoint types. #### Parameters - `app` - Express Application instance #### Rate Limiting Rules Applied 1. **API Endpoints** (`/api`, `/api/v1`) - Uses general API rate limiter - Applied to all API routes 2. **Authentication Endpoints** (`/api/auth`, `/api/v1/auth`) - Uses stricter authentication rate limiter - Applied when path includes: `/login`, `/register`, `/authenticate` 3. **Sensitive Operations** (`/api`) - Uses most restrictive sensitive operations limiter - Applied to: - Paths containing `/2fa` - Requests with specific API endpoint headers: - `auth:2fa-setup` - `auth:2fa-enable` - `auth:2fa-disable` - `auth:2fa-verify` #### Throws - `Error` - If rate limiting configuration fails ### Configuration Manager #### `configManager.setConfigSource(source: ConfigSource): void` Sets the configuration source function. ```typescript const source: ConfigSource = async () => ({ accessTokenSecret: 'your-secret', isDevelopment: false }); configManager.setConfigSource(source); ``` #### `configManager.setConfig(config: TokenSecret): void` Directly sets the configuration and emits a `configAvailable` event. ```typescript configManager.setConfig({ accessTokenSecret: 'direct-secret', isDevelopment: true }); ``` #### `configManager.getConfig(): TokenSecret | undefined` Returns the current configuration or `undefined` if not set. ```typescript const currentConfig = configManager.getConfig(); if (currentConfig) { console.log('Current secret:', currentConfig.accessTokenSecret); } ``` #### `configManager.loadConfig(): Promise<TokenSecret>` Loads configuration from the configured source. ```typescript try { const config = await configManager.loadConfig(); console.log('Config loaded:', config); } catch (error) { console.error('Failed to load config:', error); } ``` #### Event Methods ```typescript // Listen for configuration changes configManager.on('configAvailable', (config: TokenSecret) => { console.log('New config available:', config); }); // Remove event listener configManager.off('configAvailable', handler); // Emit custom events configManager.emit('customEvent', data); ``` ## Configuration ### TypeScript Interfaces #### `TokenSecret` ```typescript interface TokenSecret { accessTokenSecret: string; isDevelopment: boolean; } ``` #### `ConfigSource` ```typescript type ConfigSource = () => Promise<TokenSecret>; ``` #### `RateLimitRule` ```typescript interface RateLimitRule { paths: string[]; limiter: RequestHandler; condition?: (req: Request) => boolean; } ``` ## Rate Limiting Rules ### Rule Priority and Application Rate limiting rules are applied in the following order: 1. **General API Routes** - Broadest scope, lowest restrictions 2. **Authentication Routes** - Medium restrictions for login/register 3. **Sensitive Operations** - Highest restrictions for 2FA operations ### Custom Conditions Rules can include optional conditions that determine when the limiter should be applied: ```typescript { paths: ['/api/auth'], limiter: authLimiter, condition: (req) => req.path.includes('/login') } ``` ### Header-Based Detection The module checks for API endpoint headers to identify sensitive operations: - Primary header: `API_ENDPOINT_HEADER` - Fallback: Lowercase version of the header - Supported values: `auth:2fa-setup`, `auth:2fa-enable`, `auth:2fa-disable`, `auth:2fa-verify` ## Examples ### Basic Setup with Environment Variables ```typescript import express from 'express'; import { configureRateLimits, configManager } from 'express-limiter-pro'; const app = express(); // Configure from environment configManager.setConfigSource(async () => ({ accessTokenSecret: process.env.JWT_SECRET || 'fallback-secret', isDevelopment: process.env.NODE_ENV !== 'production' })); // Apply rate limiting configureRateLimits(app); // Load and use configuration configManager.loadConfig().then(config => { console.log(`Server starting in ${config.isDevelopment ? 'development' : 'production'} mode`); }); ``` ### Configuration with Event Handling ```typescript import { configManager } from 'express-limiter-pro'; // Set up event listener configManager.on('configAvailable', (config) => { console.log('Configuration updated:', { hasSecret: !!config.accessTokenSecret, isDevelopment: config.isDevelopment }); }); // Dynamic configuration source configManager.setConfigSource(async () => { const response = await fetch('/api/config'); return response.json(); }); await configManager.loadConfig(); ``` ### Custom Rate Limiting Setup ```typescript import express from 'express'; import rateLimit from 'express-rate-limit'; const app = express(); // You would need to implement these limiter functions const customApiLimiter = rateLimit({ windowMs: 15 * 60 * 1000, // 15 minutes max: 100 }); // Then configure with your custom limiters configureRateLimits(app); ``` ## Error Handling ### Configuration Errors The module throws `ConfigNotFoundException` in these scenarios: - Config source not set when `loadConfig()` is called - Error occurs while loading configuration from source ```typescript import { ConfigNotFoundException } from './errors/error'; try { await configManager.loadConfig(); } catch (error) { if (error instanceof ConfigNotFoundException) { console.error('Configuration error:', error.message); } } ``` ### Rate Limiting Errors If rate limiting configuration fails, the `configureRateLimits` function will: 1. Log the error using the internal logger 2. Re-throw the error for handling by the application ```typescript try { configureRateLimits(app); } catch (error) { console.error('Failed to set up rate limiting:', error); process.exit(1); } ``` ## TypeScript Support This module is written in TypeScript and includes full type definitions. All interfaces and types are exported for use in your application: ```typescript import { TokenSecret, ConfigSource, RateLimitRule } from 'express-limiter-pro'; ``` ### Type Safety The configuration manager ensures type safety through: - Strict typing of configuration objects - Promise-based async operations with proper error handling - Event emitter with typed event handlers ## Dependencies ### Required Dependencies - `express` (^4.17.0) - Express.js web framework (peer dependency) - `express-rate-limit` (^8.0.1) - Rate limiting middleware - `jsonwebtoken` (^9.0.2) - JWT token handling ### Built With - **TypeScript 5.8+** - Full type safety and modern JavaScript features - **Node.js 14+** - Modern Node.js runtime support - **Jest** - Comprehensive testing framework - **ESLint** - Code quality and consistency