照片网站源码,广州我网站制作,做网站宣传的公司,wordpress非插件幻灯业务场景为限制消息发送#xff0c;要求每天不超过一次#xff0c;每七天不超过三次。
Redission 的 RRateLimiter 虽然功能完备且支持自定义限流配置#xff0c;但是每个限流器都需要维护三个 key#xff0c;并且 lua 脚本中的判断逻辑较为复杂。
见#xff1a;Redisso…业务场景为限制消息发送要求每天不超过一次每七天不超过三次。
Redission 的 RRateLimiter 虽然功能完备且支持自定义限流配置但是每个限流器都需要维护三个 key并且 lua 脚本中的判断逻辑较为复杂。
见Redisson 分布式限流器 RRateLimiter 的使用及原理
此外本业务场景每次固定只需要获取一个令牌且时间等限流参数固定因此完全可以通过一个 sorted set 实现令牌桶限流。
对应 lua 脚本
-- sorted set 令牌桶的 key
local key KEYS[1];
-- 当前日期 格式为 yyyy-MM-dd
local member ARGV[1];
-- 当前日期 0 点对应的时间戳 单位为秒
local timestamp tonumber(ARGV[2]);local exists redis.call(exists, key);
if exists 0 then-- 创建并授权redis.call(zadd, key, timestamp, member);redis.call(expire, key, 7 * 24 * 60 * 60);return 1;
else-- 移除七天前的授权记录 本质是回收令牌local sevenDaysAgo timestamp - 7 * 24 * 60 * 60;redis.call(zremrangebyscore, key, -inf, sevenDaysAgo);-- 如果队列长度少于 3 则尝试进行授权local length redis.call(zcard, key);if length 3 thenlocal count redis.call(zcount, key, timestamp, timestamp);if (count 0) then-- 每天不超过一次redis.call(zadd, key, timestamp, member);redis.call(expire, key, 7 * 24 * 60 * 60);return 1;elsereturn 0;end;elsereturn 0;end;
end;