summaryrefslogtreecommitdiffstats
path: root/node-repository
diff options
context:
space:
mode:
authorHåkon Hallingstad <hakon@verizonmedia.com>2021-08-17 14:59:45 +0200
committerHåkon Hallingstad <hakon@verizonmedia.com>2021-08-17 14:59:45 +0200
commit662ab0f5f14f85e5bf7b5d9d50e047aa1da94657 (patch)
tree67e499b739576244aeef6930a6bc8adbe4d9cac6 /node-repository
parent252ed45c65d37440ed8908b0f3d6c78eff159c23 (diff)
Trigger redeployment of hosted-vespa.routing if there are any ready proxy nodes
Diffstat (limited to 'node-repository')
-rw-r--r--node-repository/src/main/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainer.java45
-rw-r--r--node-repository/src/test/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainerTest.java10
2 files changed, 43 insertions, 12 deletions
diff --git a/node-repository/src/main/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainer.java b/node-repository/src/main/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainer.java
index 39183688340..e5cfd4e9676 100644
--- a/node-repository/src/main/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainer.java
+++ b/node-repository/src/main/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainer.java
@@ -13,11 +13,10 @@ import com.yahoo.vespa.hosted.provision.node.History;
import java.time.Duration;
import java.time.Instant;
-import java.util.LinkedHashSet;
+import java.util.HashSet;
import java.util.Map;
import java.util.Optional;
import java.util.Set;
-import java.util.stream.Collectors;
/**
* This maintainer detects changes to nodes that must be expedited, and redeploys affected applications.
@@ -41,14 +40,29 @@ public class ExpeditedChangeApplicationMaintainer extends ApplicationMaintainer
@Override
protected Set<ApplicationId> applicationsNeedingMaintenance() {
- Map<ApplicationId, NodeList> nodesByApplication = nodeRepository().nodes().list()
- .nodeType(NodeType.tenant, NodeType.proxy)
- .matching(node -> node.allocation().isPresent())
- .groupingBy(node -> node.allocation().get().owner());
- return nodesByApplication.entrySet().stream()
- .filter(entry -> hasNodesWithChanges(entry.getKey(), entry.getValue()))
- .map(Map.Entry::getKey)
- .collect(Collectors.toCollection(LinkedHashSet::new));
+ var applications = new HashSet<ApplicationId>();
+
+ nodeRepository().nodes()
+ .list()
+ .nodeType(NodeType.tenant, NodeType.proxy)
+ .matching(node -> node.allocation().isPresent())
+ .groupingBy(node -> node.allocation().get().owner())
+ .entrySet()
+ .stream()
+ .filter(entry -> hasNodesWithChanges(entry.getKey(), entry.getValue()))
+ .map(Map.Entry::getKey)
+ .forEach(applications::add);
+
+ // A ready proxy node should trigger a redeployment as it will activates the ready node.
+ ApplicationId proxyApplicationId = ApplicationId.from("hosted-vespa", "routing", "default");
+ if (!applications.contains(proxyApplicationId)) {
+ NodeList readyProxyNodes = nodeRepository().nodes().list(Node.State.ready).nodeType(NodeType.proxy);
+ if (hasBeenReadied(proxyApplicationId, readyProxyNodes)) {
+ applications.add(proxyApplicationId);
+ }
+ }
+
+ return applications;
}
/**
@@ -63,6 +77,17 @@ public class ExpeditedChangeApplicationMaintainer extends ApplicationMaintainer
" as an expedited change was made to its nodes");
}
+ private boolean hasBeenReadied(ApplicationId applicationId, NodeList nodes) {
+ Optional<Instant> lastDeployTime = deployer().lastDeployTime(applicationId);
+ if (lastDeployTime.isEmpty()) return false;
+
+ return nodes.stream()
+ .flatMap(node -> node.history().events().stream())
+ .filter(event -> event.type() == History.Event.Type.readied)
+ .map(History.Event::at)
+ .anyMatch(e -> lastDeployTime.get().isBefore(e));
+ }
+
private boolean hasNodesWithChanges(ApplicationId applicationId, NodeList nodes) {
Optional<Instant> lastDeployTime = deployer().lastDeployTime(applicationId);
if (lastDeployTime.isEmpty()) return false;
diff --git a/node-repository/src/test/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainerTest.java b/node-repository/src/test/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainerTest.java
index 62d09c99f16..9766ade56c9 100644
--- a/node-repository/src/test/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainerTest.java
+++ b/node-repository/src/test/java/com/yahoo/vespa/hosted/provision/maintenance/ExpeditedChangeApplicationMaintainerTest.java
@@ -68,9 +68,15 @@ public class ExpeditedChangeApplicationMaintainerTest {
maintainer.maintain();
assertEquals("Operator change -> redeployment", 5, fixture.deployer.redeployments);
+ clock.advance(Duration.ofSeconds(1));
+ fixture.tester.makeReadyNodes(1, fixture.nodeResources, NodeType.proxy);
+ clock.advance(Duration.ofMinutes(2));
+ maintainer.maintain();
+ assertEquals("Ready proxy node -> redeployment", 6, fixture.deployer.redeployments);
+
clock.advance(Duration.ofMinutes(2));
maintainer.maintain();
- assertEquals("No further operator changes -> no (new) redeployments", 5, fixture.deployer.redeployments);
+ assertEquals("No further operator changes -> no (new) redeployments", 6, fixture.deployer.redeployments);
}
private static class Fixture {
@@ -82,7 +88,7 @@ public class ExpeditedChangeApplicationMaintainerTest {
final NodeResources nodeResources = new NodeResources(2, 8, 50, 1);
final ApplicationId app1 = ApplicationId.from(TenantName.from("foo1"), ApplicationName.from("bar"), InstanceName.from("fuz"));
final ApplicationId app2 = ApplicationId.from(TenantName.from("foo2"), ApplicationName.from("bar"), InstanceName.from("fuz"));
- final ApplicationId app3 = ApplicationId.from(TenantName.from("vespa-hosted"), ApplicationName.from("routing"), InstanceName.from("default"));
+ final ApplicationId app3 = ApplicationId.from(TenantName.from("hosted-vespa"), ApplicationName.from("routing"), InstanceName.from("default"));
final ClusterSpec clusterApp1 = ClusterSpec.request(ClusterSpec.Type.container, ClusterSpec.Id.from("test")).vespaVersion("6.42").build();
final ClusterSpec clusterApp2 = ClusterSpec.request(ClusterSpec.Type.content, ClusterSpec.Id.from("test")).vespaVersion("6.42").build();
final ClusterSpec clusterApp3 = ClusterSpec.request(ClusterSpec.Type.content, ClusterSpec.Id.from("routing")).vespaVersion("6.42").build();