SEC-003: Global Rate-Limiting for API and Streaming Endpoints
Background
Rate limiting previously protected only a few cache-clear/reset endpoints. Most API endpoints, plus high-cost streaming routes, were still susceptible to request flooding.
Changes
server.js- Added a global rate limiter middleware using
express-rate-limit. - Applied limiter to
['/api', '/chat', '/manual']so all API and API-like streaming calls are covered. - Added hybrid identity keying:
- API key (
x-api-key) when valid - JWT user identity (
id|userId|username|sub) when available - Fallback to client IP
- API key (
- Enabled
app.set('trust proxy', 1)for correct IP behavior behind reverse proxies. config/config.js- Added
apiKeyconfiguration fallback chain:API_KEY || PAPERLESS_AI_API_KEY. - Added global limiter config:
GLOBAL_RATE_LIMIT_WINDOW_MS(default900000)GLOBAL_RATE_LIMIT_MAX(default120)
routes/auth.js- Switched API key auth checks to
config.apiKeyfor consistency. routes/setup.js- Updated existing cache-clear limiter API key skip check to use
config.apiKey. tests/test-rate-limiting.js- Reworked test to validate global limiter scope (
/api,/chat,/manual), health exclusion, and optional 429 enforcement.
Testing
# Server starten
npm run test
# In separater Shell (optional mit niedrigem Limit für schnellen 429-Test)
GLOBAL_RATE_LIMIT_MAX=10 node tests/test-rate-limiting.js
Impact
- Security: Broad protection against request flooding for all major API entry points.
- Reliability: Better resilience for streaming endpoints under burst traffic.
- Operability: Limit values are centrally configurable via environment variables.
Upstream Status
- Not submitted
- PR opened
- Merged upstream
- Fork-local security hardening