每个 ZooKeeper 节点内部有一个状态机(QuorumPeer):它在 LOOKING、FOLLOWING、LEADING、OBSERVING 之间切换。这篇不画状态图,直接把节点日志里的 Peer state changed 按时间排出来。
+ 0 ms Peer state changed: following + 6 ms FOLLOWING - LEADER ELECTION TOOK - 430 MS + 7 ms Peer state changed: following - discovery + 14 ms Peer state changed: following - synchronization + 15 ms Peer state changed: following - synchronization - diff + 17 ms Peer state changed: following - synchronization + 39 ms Peer state changed: following - broadcast
z32-1(现在 follower):
+ -81 ms Peer state changed: following - broadcast
+ 4 ms Peer state changed: looking
+ 216 ms Peer state changed: following
+ 217 ms FOLLOWING - LEADER ELECTION TOOK - 213 MS
+ 218 ms Peer state changed: following - discovery
+ 331 ms Peer state changed: following - synchronization
+ 332 ms Peer state changed: following - synchronization - snap
+ 336 ms Peer state changed: following - synchronization
+ 344 ms Peer state changed: following - broadcast
z32-3(现在 leader):
+ -64 ms Peer state changed: following - broadcast
+ 5 ms Peer state changed: looking
+ 216 ms Peer state changed: leading
+ 223 ms LEADING - LEADER ELECTION TOOK - 218 MS
+ 226 ms Peer state changed: leading - discovery
+ 332 ms Peer state changed: leading - synchronization
+ 343 ms Peer state changed: leading - broadcast时间点来自日志时间戳与我脚本里记录的「杀」的时刻(同一台机器),所以相对值可信,绝对值有毫秒级误差。
LOOKING → 还没有 leader,在选举(此时 srvr 返回「不在服务」);FOLLOWING / LEADING / OBSERVING → 对应 Mode follower / leader / observer 重新启动原 leader 0.3 秒后看它的 srvr: Mode: follower 几秒后: follower