我在我的节点 ExpressJS 服务器中将 Redis 与 express-rate-limit 和 rate-limit-redis 一起使用。
我面临的问题是,当我的 Redis 服务器重新启动时(我知道这是不应该发生的事情,但是,我们只是认为它最终可能会发生),它会成功重新连接,但随后在下一个请求到我的服务器,我从 Redis 收到此错误:
NOSCRIPT No matching script. Please use EVAL
我读过一些有关它的信息,我发现我不是唯一一个遇到这个问题的人。
但是我还是没能找到解决办法。
我应该怎样做才能避免这个错误?我有什么选择?
编辑:找到解决方案
所以基本上,当Redis连接时,我通过
redisClient.scriptLoad
Redis客户端功能加载所需的脚本。
文件:
rate-limit.cript.lua
// Script source: https://github.com/wyattjoh/rate-limit-redis/blob/dcb5941c45325a8037bbb257882f745d9ee74b89/src/lib.ts#L58
local totalHits = redis.call("INCR", KEYS[1])
local timeToExpire = redis.call("PTTL", KEYS[1])
if timeToExpire <= 0 or ARGV[1] == "1"
then
redis.call("PEXPIRE", KEYS[1], tonumber(ARGV[2]))
timeToExpire = tonumber(ARGV[2])
end
return { totalHits, timeToExpire }
文件:
redis.js
(Redis连接管理)
const loadRateLimitScript = (redisClient) => redisClient.scriptLoad(
fs.readFileSync(`${__dirname}/../constants/luaScripts/rate-limit-script.lua`, 'utf8')
.replace(/^\s+/gm, '')
.trim()
);
class myRedis {
constructor() {
const redisClient = createClient({
url: `redis://${REDIS.HOST}:${REDIS.PORT}`
, username: REDIS.USERNAME
, password: REDIS.PASSWORD
});
redisClient.on('error', onRedisError);
redisClient.on('connect', () => {
loadRateLimitScript(redisClient);
});
redisClient.on('reconnecting', onRedisReconnecting);
redisClient.on('ready', onRedisReady);
redisClient.on('end', onRedisEnd);
this.redisClient = redisClient;
}
}