Add getPeerIds to RaftActorContext
[controller.git] / opendaylight / md-sal / sal-akka-raft / src / main / java / org / opendaylight / controller / cluster / raft / behaviors / AbstractRaftActorBehavior.java
index fd80d66ebfbc274aa676d098afba452547d7688a..8cb011f7a71d1b54b76bba86a261612f4f555bb0 100644 (file)
@@ -10,6 +10,7 @@ package org.opendaylight.controller.cluster.raft.behaviors;
 
 import akka.actor.ActorRef;
 import akka.actor.Cancellable;
+import java.util.Map;
 import java.util.Random;
 import java.util.concurrent.TimeUnit;
 import org.opendaylight.controller.cluster.raft.ClientRequestTracker;
@@ -17,6 +18,7 @@ import org.opendaylight.controller.cluster.raft.RaftActorContext;
 import org.opendaylight.controller.cluster.raft.RaftState;
 import org.opendaylight.controller.cluster.raft.ReplicatedLogEntry;
 import org.opendaylight.controller.cluster.raft.SerializationUtils;
+import org.opendaylight.controller.cluster.raft.ServerConfigurationPayload;
 import org.opendaylight.controller.cluster.raft.base.messages.ApplyJournalEntries;
 import org.opendaylight.controller.cluster.raft.base.messages.ApplyState;
 import org.opendaylight.controller.cluster.raft.base.messages.ElectionTimeout;
@@ -425,17 +427,29 @@ public abstract class AbstractRaftActorBehavior implements RaftActorBehavior {
         this.leaderPayloadVersion = leaderPayloadVersion;
     }
 
-    protected RaftActorBehavior switchBehavior(RaftActorBehavior behavior) {
-        LOG.info("{} :- Switching from behavior {} to {}", logName(), this.state(), behavior.state());
+    @Override
+    public RaftActorBehavior switchBehavior(RaftActorBehavior behavior) {
+        return internalSwitchBehavior(behavior);
+    }
+
+    protected RaftActorBehavior internalSwitchBehavior(RaftState newState) {
+        if(context.getRaftPolicy().automaticElectionsEnabled()){
+            return internalSwitchBehavior(newState.createBehavior(context));
+        }
+        return this;
+    }
+
+    private RaftActorBehavior internalSwitchBehavior(RaftActorBehavior newBehavior) {
+        LOG.info("{} :- Switching from behavior {} to {}", logName(), this.state(), newBehavior.state());
         try {
             close();
         } catch (Exception e) {
             LOG.error("{}: Failed to close behavior : {}", logName(), this.state(), e);
         }
-
-        return behavior;
+        return newBehavior;
     }
 
+
     protected int getMajorityVoteCount(int numPeers) {
         // Votes are required from a majority of the peers including self.
         // The numMajority field therefore stores a calculated value
@@ -478,4 +492,20 @@ public abstract class AbstractRaftActorBehavior implements RaftActorBehavior {
         return context.getId();
     }
 
+    public void applyServerConfiguration(ServerConfigurationPayload serverConfig) {
+        Map<String, String> currentPeers = context.getPeerAddresses();
+        for(String peerId: serverConfig.getNewServerConfig()) {
+            if(!getId().equals(peerId)) {
+                if(!currentPeers.containsKey(peerId)) {
+                    context.addToPeers(peerId, null);
+                } else {
+                    currentPeers.remove(peerId);
+                }
+            }
+        }
+
+        for(String peerIdToRemove: currentPeers.keySet()) {
+            context.removePeer(peerIdToRemove);
+        }
+    }
 }