[ONOS-7100] Make leader election timeouts configurable
Change-Id: If8c8be2ce5b4e2019039296f83a4aa417d8815bd
diff --git a/core/store/dist/src/main/java/org/onosproject/store/cluster/impl/DistributedLeadershipStore.java b/core/store/dist/src/main/java/org/onosproject/store/cluster/impl/DistributedLeadershipStore.java
index 2bb1ea3..e8dde09 100644
--- a/core/store/dist/src/main/java/org/onosproject/store/cluster/impl/DistributedLeadershipStore.java
+++ b/core/store/dist/src/main/java/org/onosproject/store/cluster/impl/DistributedLeadershipStore.java
@@ -15,6 +15,7 @@
*/
package org.onosproject.store.cluster.impl;
+import java.util.Dictionary;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.ExecutorService;
@@ -26,9 +27,12 @@
import org.apache.felix.scr.annotations.Activate;
import org.apache.felix.scr.annotations.Component;
import org.apache.felix.scr.annotations.Deactivate;
+import org.apache.felix.scr.annotations.Modified;
+import org.apache.felix.scr.annotations.Property;
import org.apache.felix.scr.annotations.Reference;
import org.apache.felix.scr.annotations.ReferenceCardinality;
import org.apache.felix.scr.annotations.Service;
+import org.onosproject.cfg.ComponentConfigService;
import org.onosproject.cluster.ClusterService;
import org.onosproject.cluster.Leadership;
import org.onosproject.cluster.LeadershipEvent;
@@ -45,8 +49,12 @@
import org.onosproject.upgrade.UpgradeEvent;
import org.onosproject.upgrade.UpgradeEventListener;
import org.onosproject.upgrade.UpgradeService;
+import org.osgi.service.component.ComponentContext;
import org.slf4j.Logger;
+import static com.google.common.base.Strings.isNullOrEmpty;
+import static org.apache.felix.scr.annotations.ReferenceCardinality.MANDATORY_UNARY;
+import static org.onlab.util.Tools.get;
import static org.onlab.util.Tools.groupedThreads;
import static org.slf4j.LoggerFactory.getLogger;
@@ -70,12 +78,20 @@
@Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
protected CoordinationService storageService;
+ @Reference(cardinality = MANDATORY_UNARY)
+ protected ComponentConfigService configService;
+
@Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
protected VersionService versionService;
@Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
protected UpgradeService upgradeService;
+ private static final long DEFAULT_ELECTION_TIMEOUT_MILLIS = 5000;
+ @Property(name = "electionTimeoutMillis", longValue = DEFAULT_ELECTION_TIMEOUT_MILLIS,
+ label = "the leader election timeout in milliseconds")
+ private long electionTimeoutMillis = DEFAULT_ELECTION_TIMEOUT_MILLIS;
+
private ExecutorService statusChangeHandler;
private NodeId localNodeId;
private LeaderElector leaderElector;
@@ -149,25 +165,54 @@
@Activate
public void activate() {
+ configService.registerProperties(getClass());
statusChangeHandler = Executors.newSingleThreadExecutor(
groupedThreads("onos/store/dist/cluster/leadership", "status-change-handler", log));
localNodeId = clusterService.getLocalNode().id();
leaderElector = storageService.leaderElectorBuilder()
- .withName("onos-leadership-elections")
- .build()
- .asLeaderElector();
+ .withName("onos-leadership-elections")
+ .withElectionTimeout(electionTimeoutMillis)
+ .build()
+ .asLeaderElector();
leaderElector.addChangeListener(leadershipChangeListener);
leaderElector.addStatusChangeListener(clientStatusListener);
upgradeService.addListener(upgradeListener);
log.info("Started");
}
+ @Modified
+ public void modified(ComponentContext context) {
+ if (context == null) {
+ return;
+ }
+
+ Dictionary<?, ?> properties = context.getProperties();
+ long newElectionTimeoutMillis;
+ try {
+ String s = get(properties, "electionTimeoutMillis");
+ newElectionTimeoutMillis = isNullOrEmpty(s) ? electionTimeoutMillis : Long.parseLong(s.trim());
+ } catch (NumberFormatException | ClassCastException e) {
+ log.warn("Malformed configuration detected; using defaults", e);
+ newElectionTimeoutMillis = DEFAULT_ELECTION_TIMEOUT_MILLIS;
+ }
+
+ if (newElectionTimeoutMillis != electionTimeoutMillis) {
+ electionTimeoutMillis = newElectionTimeoutMillis;
+ leaderElector = storageService.leaderElectorBuilder()
+ .withName("onos-leadership-elections")
+ .withElectionTimeout(electionTimeoutMillis)
+ .build()
+ .asLeaderElector();
+ }
+ }
+
@Deactivate
public void deactivate() {
leaderElector.removeChangeListener(leadershipChangeListener);
leaderElector.removeStatusChangeListener(clientStatusListener);
upgradeService.removeListener(upgradeListener);
statusChangeHandler.shutdown();
+ configService.unregisterProperties(getClass(), false);
log.info("Stopped");
}