reset configuration server state when master becomes available
Unlike the former ruby implementation, the go code continues checking
redis availability during pinging or invalidating. However, the code did
not reset state properly, leading the UI to display switch in progress.
MODIFY
go/src/github.com/xing/beetle/server.go
go/src/github.com/xing/beetle/server.go
@@ -798,13 +798,19 @@ func (s *ServerState) Pong(msg MsgBody) {
level, enough := s.ReceivedEnoughClientPongIds()
if s.pinging && enough {
logInfo("Received a sufficient number of pong ids!. Confidence level: %f.", level)
+ s.StopPinging()
+ s.InvalidateCurrentMaster()
+ }
+}
+
+// StopPinging changes the current state to 'not pinging' and cancels the
+// inavailability timer if one is active.
+func (s *ServerState) StopPinging() {
s.pinging = false
if s.availabilityTimer != nil {
s.availabilityTimer.Stop()
s.availabilityTimer = nil
}
- s.InvalidateCurrentMaster()
- }
}
// ClientStarted handles a client's CLIENT_STARTED message.
@@ -848,13 +854,19 @@ func (s *ServerState) ClientInvalidated(msg MsgBody) {
level, enough := s.ReceivedEnoughClientInvalidatedIds()
if s.invalidating && enough {
logInfo("Received a sufficient number of client invalidated ids! Confidence level: %f.", level)
+ s.StopInvalidating()
+ s.SwitchMaster()
+ }
+}
+
+// StopInvalidating changes the state to 'not invalidating' and cancels the
+// invalidation timer if one is active.
+func (s *ServerState) StopInvalidating() {
s.invalidating = false
if s.invalidateTimer != nil {
s.invalidateTimer.Stop()
s.invalidateTimer = nil
}
- s.SwitchMaster()
- }
}
// MasterUnavailable pauses the redis watcher, sends a nofication that the redis
@@ -873,7 +885,7 @@ func (s *ServerState) MasterUnavailable() {
}
}
-// MasterAvailable send current master info to all connected clients and
+// MasterAvailable sends current master info to all connected clients and
// reconfigures remaining redis servers as slaves of the (new) master.
func (s *ServerState) MasterAvailable() {
s.PublishMaster(s.currentMaster.server)
@@ -1154,17 +1166,25 @@ func (s *ServerState) StartWatcher() {
// PauseWatcher starts watching the redis server status.
func (s *ServerState) PauseWatcher() {
- if s.WatcherPaused() {
- return
- }
- logInfo("Pause checking availability of redis servers")
+ if !s.WatcherPaused() {
s.watching = false
+ logInfo("Paused checking availability of redis servers")
+ }
}
// CheckRedisAvailability uses
func (s *ServerState) CheckRedisAvailability() {
s.redis.Refresh()
if s.MasterIsAvailable() {
+ if s.pinging {
+ s.StopPinging()
+ logInfo("Redis master came online while pinging")
+ }
+ if s.invalidating {
+ s.StopInvalidating()
+ logInfo("Redis master came online while invalidating")
+ }
+ s.StartWatcher()
s.MasterAvailable()
} else {
retriesLeft := s.GetConfig().RedisMasterRetries - (s.retries + 1)

reset configuration server state when master becomes available

Unlike the former ruby implementation, the go code continues checking
redis availability during pinging or invalidating. However, the code did
not reset state properly, leading the UI to display switch in progress.