等待
Syntax
WAIT numreplicas timeout
- Available since:
- 3.0.0
- Time complexity:
- O(1)
- ACL categories:
-
@slow
,@blocking
,@connection
,
此命令会阻塞当前客户端,直到所有先前的写入命令成功传输并被至少你在numreplicas
参数中指定的副本数量确认。如果你为timeout
参数(以毫秒为单位)指定的值达到,即使尚未达到指定的副本数量,命令也会返回。
命令 将始终返回 在当前客户端发送的写命令被确认的副本数量,无论是在达到指定的副本数量时,还是在达到超时时。
几点说明:
- 当
WAIT
返回时,保证在当前连接上下文中发送的所有先前写入命令都被WAIT
返回的副本数量接收。 - 如果命令作为
MULTI
事务的一部分发送(自Redis 7.0起,任何不允许阻塞的上下文,例如脚本内部),该命令不会阻塞,而是尽快返回确认先前写入命令的副本数量。 - 超时时间为0意味着永远阻塞。
- 由于
WAIT
在失败和成功的情况下都会返回达到的副本数量,客户端应检查返回值是否等于或大于其要求的复制级别。
一致性和等待
请注意,WAIT
并不会使 Redis 成为一个强一致性存储:虽然同步复制是复制状态机的一部分,但它并不是唯一需要的。然而,在 Sentinel 或 Redis Cluster 故障转移的上下文中,WAIT
提高了实际数据的安全性。
具体来说,如果一个给定的写入操作被转移到一个或多个副本,那么在主节点失败时,我们更有可能(但不能保证)在故障转移期间提升一个接收到写入操作的副本:无论是Sentinel还是Redis集群都会尽力在可用的副本集中提升最佳的副本。
然而,这只是一个尽力而为的尝试,因此仍然有可能丢失同步复制到多个副本的写入。
实现细节
自从引入了部分重新同步与副本(PSYNC功能)以来,Redis副本会异步地向其主服务器发送它们已经在复制流中处理的偏移量的ping。这被用于多种方式:
- 检测超时的副本。
- 在断开连接后执行部分重新同步。
- 实现
WAIT
。
在WAIT
的具体实现中,Redis会记住每个客户端在执行给定写命令时产生的复制流的复制偏移量。当调用WAIT
时,Redis会检查指定数量的副本是否已经确认了这个偏移量或更大的偏移量。
示例
> SET foo bar
OK
> WAIT 1 0
(integer) 1
> WAIT 2 1000
(integer) 1
在以下示例中,第一次调用WAIT
没有使用超时,并要求写入达到1个副本。它成功返回。在第二次尝试中,我们设置了超时,并要求写入复制到两个副本。由于只有一个副本可用,一秒钟后WAIT
解除阻塞并返回1,即达到的副本数量。