name: api-rate-limiting
description: 使用令牌桶、滑动窗口和基于Redis的算法实现API速率限制,以防止滥用。适用于保护公共API、实施分层访问或防止拒绝服务攻击。
API速率限制
使用速率限制算法,采用每用户和每端点策略,保护API免受滥用。
算法
| 算法 |
优点 |
缺点 |
| 令牌桶 |
处理突发流量,平滑 |
每个用户占用内存 |
| 滑动窗口 |
准确 |
内存密集 |
| 固定窗口 |
简单 |
边界峰值 |
令牌桶 (Node.js)
class TokenBucket {
constructor(capacity, refillRate) {
this.capacity = capacity;
this.tokens = capacity;
this.refillRate = refillRate; // 每秒令牌数
this.lastRefill = Date.now();
}
consume() {
this.refill();
if (this.tokens >= 1) {
this.tokens--;
return true;
}
return false;
}
refill() {
const now = Date.now();
const elapsed = (now - this.lastRefill) / 1000;
this.tokens = Math.min(this.capacity, this.tokens + elapsed * this.refillRate);
this.lastRefill = now;
}
}
Express中间件
const rateLimit = require('express-rate-limit');
const limiter = rateLimit({
windowMs: 15 * 60 * 1000, // 15分钟
max: 100,
standardHeaders: true,
message: { error: '请求过多,请稍后再试' }
});
app.use('/api/', limiter);
响应头部
X-RateLimit-Limit: 100
X-RateLimit-Remaining: 45
X-RateLimit-Reset: 1705320000
Retry-After: 60
分层限制
| 层级 |
请求/小时 |
| 免费 |
100 |
| 专业 |
1,000 |
| 企业 |
10,000 |
最佳实践
- 使用Redis进行分布式速率限制
- 在响应中包含适当的头部
- 返回429状态码和Retry-After
- 为不同计划实施分层限制
- 监控速率限制指标
- 在负载下测试