Rate Limiting
IDP implements rate limiting to prevent abuse and protect against brute-force attacks.
Refresh Endpoint Rate Limiting
The /auth/refresh endpoint has per-IP and per-JTI (session) rate limits to prevent refresh storms.
| Limit | Default | Env Variable | Description |
|---|---|---|---|
| Per-IP | 120 req/min | IDP_REFRESH_RATE_LIMIT_IP | Limits requests from a single IP address |
| Per-JTI | 30 req/min | IDP_REFRESH_RATE_LIMIT_JTI | Limits requests for a single session |
Response
When rate limit is exceeded:
- Returns
429 Too Many Requests - Includes
Retry-Afterheader (seconds until reset) - Logs warning with request metadata
Implementation
| Component | Description |
|---|---|
| Primary | Redis-backed via @nestjs-modules/ioredis |
| Fallback | In-memory Map when Redis unavailable |
| Guard | RefreshRateLimitGuard in apps/idp/src/app/guards/ |
Configuration
# Rate limits (format: Xr/Ys where X=requests, Y=seconds)
IDP_REFRESH_RATE_LIMIT_IP=120r/60s # 120 requests per minute per IP
IDP_REFRESH_RATE_LIMIT_JTI=30r/60s # 30 requests per minute per session
Account Lifecycle Rate Limits
| Endpoint | Limit | Scope |
|---|---|---|
POST /auth/account/delete-request | 3/5min | Per-user (JWT) |
DELETE /auth/account | 5/5min | Per-user (JWT) |
POST /auth/account/restore-request | 3/5min | Per-IP |
POST /auth/account/restore | 5/5min | Per-IP |
GET /auth/account/export | 5/hour | Per-user (JWT) |
Password Reset Rate Limits
Password reset endpoints implement enumeration-resistant rate limiting:
| Endpoint | Limit | Notes |
|---|---|---|
POST /auth/forgot-password | 5/min per-IP | Always returns 204 |
POST /auth/reset-password | 5/min per-IP | Token validation |
OTP Rate Limits
OTP verification has brute-force protection:
- 5 failed attempts triggers 15-minute lockout
- Progressive backoff on repeated failures
Monitoring
Check rate limit hits in logs:
kubectl logs -n idp deployment/idp-backend | grep -i "rate limit"
Prometheus metrics (when enabled):
idp_rate_limit_exceeded_total{endpoint, scope}