计数器算法实现起来比较简单,它的基本思路是:在单位时间内(如 1 秒钟)对访问次数进行计数,如果超过设定的阈值,则拒绝后续的请求。以下是一个使用 PHP 实现的计数器算法。
完整代码
class Counter {
protected $maxCount = 100; // 设定最大请求数
protected $interval = 60; // 设定时间窗口大小,单位为秒
protected $redis = null; // Redis 连接
public function __construct($maxCount, $interval) {
$this->maxCount = $maxCount;
$this->interval = $interval;
// 建立 Redis 连接
$this->redis = new Redis();
$this->redis->connect('127.0.0.1', 6379);
}
public function check($key) {
// 获取当前计数器的值
$count = intval($this->redis->get($key));
if ($count >= $this->maxCount) {
// 超过最大允许的请求数,返回 false 表示被限流了
return false;
} else {
// 自增计数器并设置过期时间
$this->redis->multi()
->incr($key)
->expire($key, $this->interval)
->exec();
return true;
}
}
}
// 使用示例
$counter = new Counter(100, 60);
if ($counter->check('user:123')) {
// 请求处理逻辑
} else {
// 被限流了,返回错误码或提示信息
}
以上代码中,Counter
类包含了三个成员变量:$maxCount
表示最大请求数,$interval
表示时间窗口大小,$redis
是与 Redis
数据库建立的连接对象。在 check
方法中,我们首先从 Redis
中获取当前请求计数器的值,如果超过了 $maxCount
,则返回 false
表示被限流了;否则自增计数器的值,并使用 $interval
设置过期时间。如果在时间窗口内再次请求同一个 key
,则会继续自增计数器的值,直到超过 $maxCount
。