这是一个棘手的情况,因为在您的示例中,该命令不会生成错误,您错误地使用了redis.call 和redis.pcall(因为ARGV[2] 是nil,就像错误消息告诉您的那样)。所以在这两种情况下,错误都没有恢复。
这是一个 command 实际失败的示例,您可以看到不同之处:
redis 127.0.0.1:6379> set foo bar
OK
redis 127.0.0.1:6379> eval 'redis.call("hget","foo","bar")' 0
(error) ERR Error running script (call to f_9e6d82f0740926e0a70775430bda59a54d4e0664): ERR Operation against a key holding the wrong kind of value
redis 127.0.0.1:6379> eval 'redis.pcall("hget","foo","bar")' 0
(nil)
但是,你可能注意到我没有返回pcall 的结果,所以脚本返回nil。如果我返回错误命令的结果怎么办?
redis 127.0.0.1:6379> eval 'return redis.call("hget","foo","bar")' 0
(error) ERR Error running script (call to f_d0a8dce7264708876edf262052788fc90a8e8325): ERR Operation against a key holding the wrong kind of value
redis 127.0.0.1:6379> eval 'return redis.pcall("hget","foo","bar")' 0
(error) ERR Operation against a key holding the wrong kind of value
使用call 没有任何变化,因为在函数有机会返回之前抛出了错误(将其视为其他语言中的异常 - Java、Python 等)。
虽然使用pcall,函数调用返回一个带有单个err 字段的表,该字段被Redis 转换为“错误回复”,所以你看不到它。你怎么能检查呢?线性化它!
redis 127.0.0.1:6379> eval 'local t = redis.pcall("hget","foo","bar"); local r = {type(t)}; for k,v in pairs(t) do r[#r+1] = k; r[#r+1] = v; end; return r' 0
1) "table"
2) "err"
3) "ERR Operation against a key holding the wrong kind of value"