summaryrefslogtreecommitdiffstats
path: root/container-core/src/main/java/com/yahoo/container/di/ConfigRetriever.java
diff options
context:
space:
mode:
Diffstat (limited to 'container-core/src/main/java/com/yahoo/container/di/ConfigRetriever.java')
-rw-r--r--container-core/src/main/java/com/yahoo/container/di/ConfigRetriever.java87
1 files changed, 42 insertions, 45 deletions
diff --git a/container-core/src/main/java/com/yahoo/container/di/ConfigRetriever.java b/container-core/src/main/java/com/yahoo/container/di/ConfigRetriever.java
index 1e7f3e06049..ff238bd2497 100644
--- a/container-core/src/main/java/com/yahoo/container/di/ConfigRetriever.java
+++ b/container-core/src/main/java/com/yahoo/container/di/ConfigRetriever.java
@@ -5,9 +5,9 @@ import com.google.common.collect.Sets;
import com.yahoo.config.ConfigInstance;
import com.yahoo.container.di.componentgraph.core.Keys;
import com.yahoo.container.di.config.Subscriber;
+import com.yahoo.container.di.config.SubscriberFactory;
import com.yahoo.vespa.config.ConfigKey;
-import java.util.Collections;
import java.util.HashSet;
import java.util.Map;
import java.util.Optional;
@@ -29,20 +29,21 @@ public final class ConfigRetriever {
private final Set<ConfigKey<? extends ConfigInstance>> bootstrapKeys;
private Set<ConfigKey<? extends ConfigInstance>> componentSubscriberKeys;
+
+ private final SubscriberFactory subscriberFactory;
private final Subscriber bootstrapSubscriber;
private Subscriber componentSubscriber;
- private final Function<Set<ConfigKey<? extends ConfigInstance>>, Subscriber> subscribe;
+ private int componentSubscriberIndex;
- public ConfigRetriever(Set<ConfigKey<? extends ConfigInstance>> bootstrapKeys,
- Function<Set<ConfigKey<? extends ConfigInstance>>, Subscriber> subscribe) {
+ public ConfigRetriever(Set<ConfigKey<? extends ConfigInstance>> bootstrapKeys, SubscriberFactory subscriberFactory) {
this.bootstrapKeys = bootstrapKeys;
this.componentSubscriberKeys = new HashSet<>();
- this.subscribe = subscribe;
+ this.subscriberFactory = subscriberFactory;
if (bootstrapKeys.isEmpty()) {
throw new IllegalArgumentException("Bootstrap key set is empty");
}
- this.bootstrapSubscriber = subscribe.apply(bootstrapKeys);
- this.componentSubscriber = subscribe.apply(componentSubscriberKeys);
+ this.bootstrapSubscriber = this.subscriberFactory.getSubscriber(bootstrapKeys, "bootstrap");
+ this.componentSubscriber = this.subscriberFactory.getSubscriber(componentSubscriberKeys, "component_" + ++componentSubscriberIndex);
}
public ConfigSnapshot getConfigs(Set<ConfigKey<? extends ConfigInstance>> componentConfigKeys,
@@ -51,55 +52,56 @@ public final class ConfigRetriever {
while (true) {
Optional<ConfigSnapshot> maybeSnapshot = getConfigsOnce(componentConfigKeys, leastGeneration, isInitializing);
if (maybeSnapshot.isPresent()) {
- var configSnapshot = maybeSnapshot.get();
- resetComponentSubscriberIfBootstrap(configSnapshot);
- return configSnapshot;
+ return maybeSnapshot.get();
}
}
}
- Optional<ConfigSnapshot> getConfigsOnce(Set<ConfigKey<? extends ConfigInstance>> componentConfigKeys,
- long leastGeneration, boolean isInitializing) {
+ private Optional<ConfigSnapshot> getConfigsOnce(Set<ConfigKey<? extends ConfigInstance>> componentConfigKeys,
+ long leastGeneration, boolean isInitializing) {
if (!Sets.intersection(componentConfigKeys, bootstrapKeys).isEmpty()) {
throw new IllegalArgumentException(
"Component config keys [" + componentConfigKeys + "] overlaps with bootstrap config keys [" + bootstrapKeys + "]");
}
- log.log(FINE, () -> "getConfigsOnce: " + componentConfigKeys);
-
Set<ConfigKey<? extends ConfigInstance>> allKeys = new HashSet<>(componentConfigKeys);
allKeys.addAll(bootstrapKeys);
setupComponentSubscriber(allKeys);
- return getConfigsOptional(leastGeneration, isInitializing);
+ var maybeSnapshot = getConfigsOptional(leastGeneration, isInitializing);
+ log.log(FINE, () -> "getConfigsOnce returning " + maybeSnapshot);
+ return maybeSnapshot;
}
private Optional<ConfigSnapshot> getConfigsOptional(long leastGeneration, boolean isInitializing) {
- long newestComponentGeneration = componentSubscriber.waitNextGeneration(isInitializing);
- log.log(FINE, () -> "getConfigsOptional: new component generation: " + newestComponentGeneration);
+ if (componentSubscriber.generation() < bootstrapSubscriber.generation()) {
+ return getComponentsSnapshot(leastGeneration, isInitializing);
+ }
+ long newestBootstrapGeneration = bootstrapSubscriber.waitNextGeneration(isInitializing);
+ log.log(FINE, () -> "getConfigsOptional: new bootstrap generation: " + newestBootstrapGeneration);
+
+ // leastGeneration is used to ensure newer generation (than the latest bootstrap or component gen)
+ // when the previous generation was invalidated due to an exception upon creating the component graph.
+ if (newestBootstrapGeneration < leastGeneration) {
+ return Optional.empty();
+ }
+ return bootstrapConfigIfChanged();
+ }
- // leastGeneration is only used to ensure newer generation when the previous generation was invalidated due to an exception
+ private Optional<ConfigSnapshot> getComponentsSnapshot(long leastGeneration, boolean isInitializing) {
+ long newestBootstrapGeneration = bootstrapSubscriber.generation();
+ long newestComponentGeneration = componentSubscriber.waitNextGeneration(isInitializing);
if (newestComponentGeneration < leastGeneration) {
+ log.log(FINE, () -> "Component generation too old: " + componentSubscriber.generation() + " < " + leastGeneration);
return Optional.empty();
- } else if (bootstrapSubscriber.generation() < newestComponentGeneration) {
- long newestBootstrapGeneration = bootstrapSubscriber.waitNextGeneration(isInitializing);
- log.log(FINE, () -> "getConfigsOptional: new bootstrap generation: " + bootstrapSubscriber.generation());
- Optional<ConfigSnapshot> bootstrapConfig = bootstrapConfigIfChanged();
- if (bootstrapConfig.isPresent()) {
- return bootstrapConfig;
- } else {
- if (newestBootstrapGeneration == newestComponentGeneration) {
- log.log(FINE, () -> "Got new components configs with unchanged bootstrap configs.");
- return componentsConfigIfChanged();
- } else {
- // This should not be a normal case, and hence a warning to allow investigation.
- log.warning("Did not get same generation for bootstrap (" + newestBootstrapGeneration +
- ") and components configs (" + newestComponentGeneration + ").");
- return Optional.empty();
- }
- }
- } else {
- // bootstrapGen==componentGen (happens only when a new component subscriber returns first config after bootstrap)
+ }
+ if (newestComponentGeneration == newestBootstrapGeneration) {
+ log.log(FINE, () -> "getConfigsOptional: new component generation: " + componentSubscriber.generation());
return componentsConfigIfChanged();
+ } else {
+ // Should not be a normal case, and hence a warning to allow investigation.
+ log.warning("Did not get same generation for bootstrap (" + newestBootstrapGeneration +
+ ") and components configs (" + newestComponentGeneration + ").");
+ return Optional.empty();
}
}
@@ -120,19 +122,14 @@ public final class ConfigRetriever {
}
}
- private void resetComponentSubscriberIfBootstrap(ConfigSnapshot snapshot) {
- if (snapshot instanceof BootstrapConfigs) {
- setupComponentSubscriber(Collections.emptySet());
- }
- }
-
private void setupComponentSubscriber(Set<ConfigKey<? extends ConfigInstance>> keys) {
if (! componentSubscriberKeys.equals(keys)) {
componentSubscriber.close();
+ log.log(FINE, () -> "Closed " + componentSubscriber);
componentSubscriberKeys = keys;
try {
- log.log(FINE, () -> "Setting up new component subscriber for keys: " + keys);
- componentSubscriber = subscribe.apply(keys);
+ componentSubscriber = subscriberFactory.getSubscriber(keys, "component_" + ++componentSubscriberIndex);
+ log.log(FINE, () -> "Set up new subscriber " + componentSubscriber + " for keys: " + keys);
} catch (Throwable e) {
log.log(Level.WARNING, "Failed setting up subscriptions for component configs: " + e.getMessage());
log.log(Level.WARNING, "Config keys: " + keys);