diff options
10 files changed, 25 insertions, 111 deletions
diff --git a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/ServiceRegistry.java b/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/ServiceRegistry.java index 52f687e5708..33a87e82ec9 100644 --- a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/ServiceRegistry.java +++ b/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/ServiceRegistry.java @@ -29,7 +29,6 @@ import com.yahoo.vespa.hosted.controller.api.integration.organization.Mailer; import com.yahoo.vespa.hosted.controller.api.integration.organization.OwnershipIssues; import com.yahoo.vespa.hosted.controller.api.integration.organization.SystemMonitor; import com.yahoo.vespa.hosted.controller.api.integration.resource.CostReportConsumer; -import com.yahoo.vespa.hosted.controller.api.integration.resource.MeteringClient; import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceDatabaseClient; import com.yahoo.vespa.hosted.controller.api.integration.secrets.TenantSecretService; import com.yahoo.vespa.hosted.controller.api.integration.user.RoleMaintainer; @@ -63,8 +62,6 @@ public interface ServiceRegistry { EndpointCertificateValidator endpointCertificateValidator(); - MeteringClient meteringService(); - ContactRetriever contactRetriever(); IssueHandler issueHandler(); diff --git a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/resource/MeteringClient.java b/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/resource/MeteringClient.java deleted file mode 100644 index 944a5eaf696..00000000000 --- a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/resource/MeteringClient.java +++ /dev/null @@ -1,24 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -package com.yahoo.vespa.hosted.controller.api.integration.resource; - -import com.yahoo.config.provision.ApplicationName; -import com.yahoo.config.provision.TenantName; - -import java.time.YearMonth; -import java.util.Collection; -import java.util.List; - -/** - * Consumes and retrieves snapshots of resources allocated per application. - * - * @author olaa - */ -public interface MeteringClient { - - void consume(Collection<ResourceSnapshot> resources); - - List<ResourceSnapshot> getSnapshotHistoryForTenant(TenantName tenantName, YearMonth yearMonth); - - void refresh(); - -} diff --git a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/resource/ResourceDatabaseClientMock.java b/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/resource/ResourceDatabaseClientMock.java index c680990e240..e9bfc4fe78c 100644 --- a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/resource/ResourceDatabaseClientMock.java +++ b/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/resource/ResourceDatabaseClientMock.java @@ -1,7 +1,6 @@ // Copyright 2019 Oath Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. package com.yahoo.vespa.hosted.controller.api.integration.resource; -import com.yahoo.config.provision.ApplicationName; import com.yahoo.config.provision.TenantName; import com.yahoo.vespa.hosted.controller.api.integration.billing.Plan; import com.yahoo.vespa.hosted.controller.api.integration.billing.PlanRegistry; @@ -9,9 +8,7 @@ import com.yahoo.vespa.hosted.controller.api.integration.billing.PlanRegistry; import java.math.BigDecimal; import java.time.Duration; import java.time.Instant; -import java.time.LocalDate; import java.time.YearMonth; -import java.time.ZoneId; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; @@ -104,7 +101,7 @@ public class ResourceDatabaseClientMock implements ResourceDatabaseClient { public List<ResourceUsage> getResourceSnapshotsForPeriod(TenantName tenantName, long start, long end) { var tenantPlan = planMap.getOrDefault(tenantName, planRegistry.defaultPlan()); - var snapshotsPerDeployment = resourceSnapshots.stream() + return resourceSnapshots.stream() .filter(snapshot -> snapshot.getTimestamp().isAfter(Instant.ofEpochMilli(start))) .filter(snapshot -> snapshot.getTimestamp().isBefore(Instant.ofEpochMilli(end))) .filter(snapshot -> snapshot.getApplicationId().tenant().equals(tenantName)) @@ -117,8 +114,6 @@ public class ResourceDatabaseClientMock implements ResourceDatabaseClient { .filter(Optional::isPresent) .map(Optional::get) .collect(Collectors.toList()); - - return snapshotsPerDeployment; } @Override @@ -133,4 +128,8 @@ public class ResourceDatabaseClientMock implements ResourceDatabaseClient { public boolean hasRefreshedMaterializedView() { return hasRefreshedMaterializedView; } + + public List<ResourceSnapshot> resourceSnapshots() { + return resourceSnapshots; + } } diff --git a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/stubs/MockMeteringClient.java b/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/stubs/MockMeteringClient.java deleted file mode 100644 index ca094f98607..00000000000 --- a/controller-api/src/main/java/com/yahoo/vespa/hosted/controller/api/integration/stubs/MockMeteringClient.java +++ /dev/null @@ -1,53 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -package com.yahoo.vespa.hosted.controller.api.integration.stubs; - -import com.yahoo.config.provision.TenantName; -import com.yahoo.vespa.hosted.controller.api.integration.resource.MeteringData; -import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceSnapshot; -import com.yahoo.vespa.hosted.controller.api.integration.resource.MeteringClient; - -import java.time.YearMonth; -import java.util.ArrayList; -import java.util.Collection; -import java.util.List; -import java.util.Map; -import java.util.Optional; -import java.util.stream.Collectors; - -/** - * @author olaa - */ -public class MockMeteringClient implements MeteringClient { - - private Collection<ResourceSnapshot> resources = new ArrayList<>(); - private Optional<MeteringData> meteringData; - private boolean isRefreshed = false; - - @Override - public void consume(Collection<ResourceSnapshot> resources){ - this.resources = resources; - } - - @Override - public List<ResourceSnapshot> getSnapshotHistoryForTenant(TenantName tenantName, YearMonth yearMonth) { - return new ArrayList<>(resources); - } - - @Override - public void refresh() { - isRefreshed = true; - } - - public Collection<ResourceSnapshot> consumedResources() { - return this.resources; - } - - public void setMeteringData(MeteringData meteringData) { - this.meteringData = Optional.of(meteringData); - this.resources = meteringData.getSnapshotHistory().entrySet().stream().map(Map.Entry::getValue).flatMap(List::stream).collect(Collectors.toList()); - } - - public boolean isRefreshed() { - return isRefreshed; - } -} diff --git a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ControllerMaintenance.java b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ControllerMaintenance.java index 193d171e334..3beb4149938 100644 --- a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ControllerMaintenance.java +++ b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ControllerMaintenance.java @@ -58,7 +58,7 @@ public class ControllerMaintenance extends AbstractComponent { maintainers.add(new ContactInformationMaintainer(controller, intervals.contactInformationMaintainer)); maintainers.add(new NameServiceDispatcher(controller, intervals.nameServiceDispatcher)); maintainers.add(new CostReportMaintainer(controller, intervals.costReportMaintainer, controller.serviceRegistry().costReportConsumer())); - maintainers.add(new ResourceMeterMaintainer(controller, intervals.resourceMeterMaintainer, metric, controller.serviceRegistry().meteringService())); + maintainers.add(new ResourceMeterMaintainer(controller, intervals.resourceMeterMaintainer, metric, controller.serviceRegistry().resourceDatabase())); maintainers.add(new CloudEventTracker(controller, intervals.cloudEventReporter)); maintainers.add(new ResourceTagMaintainer(controller, intervals.resourceTagMaintainer, controller.serviceRegistry().resourceTagger())); maintainers.add(new SystemRoutingPolicyMaintainer(controller, intervals.systemRoutingPolicyMaintainer)); diff --git a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainer.java b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainer.java index d4905f7e20a..b7d3a882ae2 100644 --- a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainer.java +++ b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainer.java @@ -17,6 +17,7 @@ import com.yahoo.vespa.hosted.controller.api.integration.configserver.NodeFilter import com.yahoo.vespa.hosted.controller.api.integration.configserver.NodeRepository; import com.yahoo.vespa.hosted.controller.api.integration.resource.MeteringClient; import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceAllocation; +import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceDatabaseClient; import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceSnapshot; import com.yahoo.vespa.hosted.controller.application.SystemApplication; import com.yahoo.vespa.hosted.controller.application.TenantAndApplicationId; @@ -57,7 +58,7 @@ public class ResourceMeterMaintainer extends ControllerMaintainer { private final ApplicationController applications; private final NodeRepository nodeRepository; - private final MeteringClient meteringClient; + private final ResourceDatabaseClient resourceClient; private final CuratorDb curator; private final SystemName systemName; private final Metric metric; @@ -71,11 +72,11 @@ public class ResourceMeterMaintainer extends ControllerMaintainer { public ResourceMeterMaintainer(Controller controller, Duration interval, Metric metric, - MeteringClient meteringClient) { + ResourceDatabaseClient resourceClient) { super(controller, interval); this.applications = controller.applications(); this.nodeRepository = controller.serviceRegistry().configServer().nodeRepository(); - this.meteringClient = meteringClient; + this.resourceClient = resourceClient; this.curator = controller.curator(); this.systemName = controller.serviceRegistry().zoneRegistry().system(); this.metric = metric; @@ -124,13 +125,13 @@ public class ResourceMeterMaintainer extends ControllerMaintainer { } private void reportResourceSnapshots(Collection<ResourceSnapshot> resourceSnapshots) { - meteringClient.consume(resourceSnapshots); + resourceClient.writeResourceSnapshots(resourceSnapshots); updateMeteringMetrics(resourceSnapshots); try (var lock = curator.lockMeteringRefreshTime()) { if (needsRefresh(curator.readMeteringRefreshTime())) { - meteringClient.refresh(); + resourceClient.refreshMaterializedView(); curator.writeMeteringRefreshTime(clock.millis()); } } catch (TimeoutException ignored) { diff --git a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/ControllerApiHandler.java b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/ControllerApiHandler.java index 346e61c907c..0c0680d9166 100644 --- a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/ControllerApiHandler.java +++ b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/ControllerApiHandler.java @@ -84,7 +84,7 @@ public class ControllerApiHandler extends AuditLoggingRequestHandler { if (path.matches("/controller/v1/maintenance/")) return new JobsResponse(controller.jobControl()); if (path.matches("/controller/v1/stats")) return new StatsResponse(controller); if (path.matches("/controller/v1/jobs/upgrader")) return new UpgraderResponse(maintenance.upgrader()); - if (path.matches("/controller/v1/metering/tenant/{tenant}/month/{month}")) return new MeteringResponse(controller.serviceRegistry().meteringService(), path.get("tenant"), path.get("month")); + if (path.matches("/controller/v1/metering/tenant/{tenant}/month/{month}")) return new MeteringResponse(controller.serviceRegistry().resourceDatabase(), path.get("tenant"), path.get("month")); return notFound(path); } diff --git a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/MeteringResponse.java b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/MeteringResponse.java index 33cd4948a7e..17461aafd02 100644 --- a/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/MeteringResponse.java +++ b/controller-server/src/main/java/com/yahoo/vespa/hosted/controller/restapi/controller/MeteringResponse.java @@ -5,7 +5,7 @@ import com.yahoo.config.provision.TenantName; import com.yahoo.restapi.SlimeJsonResponse; import com.yahoo.slime.Cursor; import com.yahoo.slime.Slime; -import com.yahoo.vespa.hosted.controller.api.integration.resource.MeteringClient; +import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceDatabaseClient; import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceSnapshot; import java.time.YearMonth; @@ -16,14 +16,14 @@ import java.util.List; */ public class MeteringResponse extends SlimeJsonResponse { - public MeteringResponse(MeteringClient meteringClient, String tenantName, String month) { - super(toSlime(meteringClient, tenantName, month)); + public MeteringResponse(ResourceDatabaseClient resourceClient, String tenantName, String month) { + super(toSlime(resourceClient, tenantName, month)); } - private static Slime toSlime(MeteringClient meteringClient, String tenantName, String month) { + private static Slime toSlime(ResourceDatabaseClient resourceClient, String tenantName, String month) { Slime slime = new Slime(); Cursor root = slime.setArray(); - List<ResourceSnapshot> snapshots = meteringClient.getSnapshotHistoryForTenant(TenantName.from(tenantName), YearMonth.parse(month)); + List<ResourceSnapshot> snapshots = resourceClient.getRawSnapshotHistoryForTenant(TenantName.from(tenantName), YearMonth.parse(month)); snapshots.forEach(snapshot -> { Cursor object = root.addObject(); object.setString("applicationId", snapshot.getApplicationId().toShortString()); diff --git a/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/integration/ServiceRegistryMock.java b/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/integration/ServiceRegistryMock.java index a91d81bb0c5..650fda3c811 100644 --- a/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/integration/ServiceRegistryMock.java +++ b/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/integration/ServiceRegistryMock.java @@ -43,7 +43,6 @@ import com.yahoo.vespa.hosted.controller.api.integration.stubs.DummyOwnershipIss import com.yahoo.vespa.hosted.controller.api.integration.stubs.DummySystemMonitor; import com.yahoo.vespa.hosted.controller.api.integration.stubs.LoggingDeploymentIssues; import com.yahoo.vespa.hosted.controller.api.integration.stubs.MockMailer; -import com.yahoo.vespa.hosted.controller.api.integration.stubs.MockMeteringClient; import com.yahoo.vespa.hosted.controller.api.integration.stubs.MockRunDataStore; import com.yahoo.vespa.hosted.controller.api.integration.stubs.MockTesterCloud; import com.yahoo.vespa.hosted.controller.api.integration.user.RoleMaintainer; @@ -68,7 +67,6 @@ public class ServiceRegistryMock extends AbstractComponent implements ServiceReg private final MockMailer mockMailer = new MockMailer(); private final EndpointCertificateMock endpointCertificateMock = new EndpointCertificateMock(clock); private final EndpointCertificateValidatorMock endpointCertificateValidatorMock = new EndpointCertificateValidatorMock(); - private final MockMeteringClient mockMeteringClient = new MockMeteringClient(); private final MockContactRetriever mockContactRetriever = new MockContactRetriever(); private final MockIssueHandler mockIssueHandler = new MockIssueHandler(); private final DummyOwnershipIssues dummyOwnershipIssues = new DummyOwnershipIssues(); @@ -148,11 +146,6 @@ public class ServiceRegistryMock extends AbstractComponent implements ServiceReg } @Override - public MockMeteringClient meteringService() { - return mockMeteringClient; - } - - @Override public MockContactRetriever contactRetriever() { return mockContactRetriever; } diff --git a/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainerTest.java b/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainerTest.java index f9441f76a38..320938f00e4 100644 --- a/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainerTest.java +++ b/controller-server/src/test/java/com/yahoo/vespa/hosted/controller/maintenance/ResourceMeterMaintainerTest.java @@ -9,9 +9,10 @@ import com.yahoo.config.provision.NodeType; import com.yahoo.config.provision.SystemName; import com.yahoo.config.provision.zone.ZoneId; import com.yahoo.vespa.hosted.controller.ControllerTester; +import com.yahoo.vespa.hosted.controller.api.integration.billing.PlanRegistryMock; import com.yahoo.vespa.hosted.controller.api.integration.configserver.Node; +import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceDatabaseClientMock; import com.yahoo.vespa.hosted.controller.api.integration.resource.ResourceSnapshot; -import com.yahoo.vespa.hosted.controller.api.integration.stubs.MockMeteringClient; import com.yahoo.vespa.hosted.controller.application.pkg.ApplicationPackage; import com.yahoo.vespa.hosted.controller.deployment.ApplicationPackageBuilder; import com.yahoo.vespa.hosted.controller.deployment.DeploymentTester; @@ -38,10 +39,10 @@ import static org.junit.Assert.assertTrue; public class ResourceMeterMaintainerTest { private final ControllerTester tester = new ControllerTester(SystemName.Public); - private final MockMeteringClient snapshotConsumer = new MockMeteringClient(); + private final ResourceDatabaseClientMock resourceClient = new ResourceDatabaseClientMock(new PlanRegistryMock()); private final MetricsMock metrics = new MetricsMock(); private final ResourceMeterMaintainer maintainer = - new ResourceMeterMaintainer(tester.controller(), Duration.ofMinutes(5), metrics, snapshotConsumer); + new ResourceMeterMaintainer(tester.controller(), Duration.ofMinutes(5), metrics, resourceClient); @Test public void updates_deployment_costs() { @@ -89,7 +90,7 @@ public class ResourceMeterMaintainerTest { long lastRefreshTime = tester.clock().millis(); tester.curator().writeMeteringRefreshTime(lastRefreshTime); maintainer.maintain(); - Collection<ResourceSnapshot> consumedResources = snapshotConsumer.consumedResources(); + Collection<ResourceSnapshot> consumedResources = resourceClient.resourceSnapshots(); // The mocked repository contains two applications, so we should also consume two ResourceSnapshots assertEquals(4, consumedResources.size()); @@ -110,13 +111,13 @@ public class ResourceMeterMaintainerTest { assertEquals(40d, (Double) metrics.getMetric(context -> "tenant2".equals(context.get("tenant")), "metering.vcpu").get(), Double.MIN_VALUE); // Metering is not refreshed - assertFalse(snapshotConsumer.isRefreshed()); + assertFalse(resourceClient.hasRefreshedMaterializedView()); assertEquals(lastRefreshTime, tester.curator().readMeteringRefreshTime()); var millisAdvanced = 3600 * 1000; tester.clock().advance(Duration.ofMillis(millisAdvanced)); maintainer.maintain(); - assertTrue(snapshotConsumer.isRefreshed()); + assertTrue(resourceClient.hasRefreshedMaterializedView()); assertEquals(lastRefreshTime + millisAdvanced, tester.curator().readMeteringRefreshTime()); } |