假设我的客户端向redis服务器发送'INCR'命令,但响应数据包丢失,因此我的客户端的read()将超时,但客户端无法判断服务器是否已执行INCR操作。
接下来该做什么?重新发送INCR或继续下一个命令?如果客户端重新发送INCR,但如果redis之前在服务器端执行过INCR,则该密钥将增加两次,这不是我们想要的。
答案 0 :(得分:2)
这不是Redis特有的问题:它也适用于任何其他数据存储(包括事务性数据存储)。这个问题没有解决办法:你只能希望尽量减少这个问题。
例如,有些人倾向于为超时设置非常激进的值,认为Redis应该是一个软实时数据存储。 Redis速度很快,但您还需要考虑网络和系统本身。与网络相关的问题可能会产生高延迟。如果系统开始交换,则会严重影响Redis的响应时间。
我倾向于认为在任何Unix / Linux系统上放置超时不到2秒都是胡说八道,如果涉及网络,我会更舒服10秒。人们提出非常低的价值,因为他们想避免他们的申请阻止:这是一个错误。他们应该将应用程序设计为异步并设置合理的超时,而不是设置非常低的超时并使应用程序保持同步。
超时后,客户端永远不应该“继续”下一个命令。它应该关闭连接,并尝试打开一个新连接。如果回复(或查询)丢失,则客户端和服务器不太可能重新同步。关闭连接更安全。
重新连接后,您是否应该尝试再次发出INCR?这完全取决于你。但是如果刚刚触发了读取超时,那么重新连接也很有可能会超时。 Redis是单线程的,当一个连接速度很慢时,所有连接的速度都很慢。