summaryrefslogtreecommitdiffstats
path: root/tenant-cd
diff options
context:
space:
mode:
authorJon Marius Venstad <jvenstad@yahoo-inc.com>2019-06-13 13:52:18 +0200
committerJon Marius Venstad <jvenstad@yahoo-inc.com>2019-06-13 13:52:18 +0200
commit2bb71582b979a83a39260f3f11466737b94ee47f (patch)
treeac4d17548ae440348a7ecd62bbd87cfa998c6496 /tenant-cd
parent7d2366a939f64f964a208e01c4455dd530f833c6 (diff)
Wrap TestConfig in TestRuntime, which includes and Authenticator, and obtain the former from controller
Diffstat (limited to 'tenant-cd')
-rw-r--r--tenant-cd/src/main/java/ai/vespa/hosted/cd/TestConfig.java101
-rw-r--r--tenant-cd/src/main/java/ai/vespa/hosted/cd/TestRuntime.java77
-rw-r--r--tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpDeployment.java15
-rw-r--r--tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpEndpoint.java8
4 files changed, 95 insertions, 106 deletions
diff --git a/tenant-cd/src/main/java/ai/vespa/hosted/cd/TestConfig.java b/tenant-cd/src/main/java/ai/vespa/hosted/cd/TestConfig.java
deleted file mode 100644
index e441254cff7..00000000000
--- a/tenant-cd/src/main/java/ai/vespa/hosted/cd/TestConfig.java
+++ /dev/null
@@ -1,101 +0,0 @@
-package ai.vespa.hosted.cd;
-
-import ai.vespa.hosted.api.ControllerHttpClient;
-import ai.vespa.hosted.auth.Authenticator;
-import com.yahoo.config.provision.ApplicationId;
-import com.yahoo.config.provision.SystemName;
-import com.yahoo.slime.ArrayTraverser;
-import com.yahoo.slime.Inspector;
-import com.yahoo.slime.JsonDecoder;
-import com.yahoo.slime.ObjectTraverser;
-import com.yahoo.config.provision.zone.ZoneId;
-import com.yahoo.slime.Slime;
-
-import java.net.URI;
-import java.nio.file.Files;
-import java.nio.file.Paths;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * The place to obtain environment-dependent configuration for the current test run.
- *
- * If the system property 'vespa.test.config' is set, this class attempts to parse config
- * from a JSON file at that location -- otherwise, attempts to access the config will return null.
- *
- * @author jvenstad
- */
-public class TestConfig {
-
- private static TestConfig theConfig;
-
- private final ApplicationId application;
- private final ZoneId zone;
- private final SystemName system;
- private final Map<ZoneId, Deployment> deployments;
-
- private TestConfig(ApplicationId application, ZoneId zone, SystemName system, Map<ZoneId, Deployment> deployments) {
- this.application = application;
- this.zone = zone;
- this.system = system;
- this.deployments = Map.copyOf(deployments);
- }
-
- /** Returns the config for this test, or null if it has not been provided. */
- public static synchronized TestConfig get() {
- if (theConfig == null) {
- String configPath = System.getProperty("vespa.test.config");
- theConfig = configPath != null ? fromFile(configPath) : fromController();
- }
- return theConfig;
- }
-
- /** Returns the full id of the application to be tested. */
- public ApplicationId application() { return application; }
-
- /** Returns the zone of the deployment to test. */
- public ZoneId zone() { return zone; }
-
- /** Returns an immutable view of all configured endpoints for each zone of the application to test. */
- public Map<ZoneId, Deployment> allDeployments() { return deployments; }
-
- /** Returns the deployment to test in this test runtime. */
- public Deployment deploymentToTest() { return deployments.get(zone); }
-
- /** Returns the system this is run against. */
- public SystemName system() { return system; }
-
- static TestConfig fromFile(String path) {
- if (path == null)
- return null;
-
- try {
- return fromJson(Files.readAllBytes(Paths.get(path)));
- }
- catch (Exception e) {
- throw new IllegalArgumentException("Failed reading config from '" + path + "'!", e);
- }
- }
-
- static TestConfig fromController() {
- ControllerHttpClient controller = new Authenticator().controller();
- return null;
- }
-
- static TestConfig fromJson(byte[] jsonBytes) {
- Inspector config = new JsonDecoder().decode(new Slime(), jsonBytes).get();
- ApplicationId application = ApplicationId.fromSerializedForm(config.field("application").asString());
- ZoneId zone = ZoneId.from(config.field("zone").asString());
- SystemName system = SystemName.from(config.field("system").asString());
- Map<ZoneId, Deployment> endpoints = new HashMap<>();
- config.field("endpoints").traverse((ObjectTraverser) (zoneId, endpointArray) -> {
- List<URI> uris = new ArrayList<>();
- endpointArray.traverse((ArrayTraverser) (__, uri) -> uris.add(URI.create(uri.asString())));
- endpoints.put(ZoneId.from(zoneId), null); // TODO jvenstad
- });
- return new TestConfig(application, zone, system, endpoints);
- }
-
-}
diff --git a/tenant-cd/src/main/java/ai/vespa/hosted/cd/TestRuntime.java b/tenant-cd/src/main/java/ai/vespa/hosted/cd/TestRuntime.java
new file mode 100644
index 00000000000..fa09d7037c9
--- /dev/null
+++ b/tenant-cd/src/main/java/ai/vespa/hosted/cd/TestRuntime.java
@@ -0,0 +1,77 @@
+package ai.vespa.hosted.cd;
+
+import ai.vespa.hosted.api.Authenticator;
+import ai.vespa.hosted.api.ControllerHttpClient;
+import ai.vespa.hosted.api.Properties;
+import ai.vespa.hosted.api.TestConfig;
+import com.yahoo.config.provision.ApplicationId;
+import com.yahoo.config.provision.Environment;
+import com.yahoo.config.provision.RegionName;
+import com.yahoo.config.provision.zone.ZoneId;
+
+import java.nio.file.Files;
+import java.nio.file.Paths;
+
+import static ai.vespa.hosted.api.TestConfig.fromJson;
+
+/**
+ * The place to obtain environment-dependent configuration for test of a Vespa deployment.
+ *
+ * @author jvenstad
+ */
+public class TestRuntime {
+
+ private static TestRuntime theRuntime;
+
+ private final TestConfig config;
+ private final Authenticator authenticator;
+
+ private TestRuntime(TestConfig config, Authenticator authenticator) {
+ this.config = config;
+ this.authenticator = authenticator;
+ }
+
+ /**
+ * Returns the config for this test, or null if it has not been provided.
+ *
+ * If the system property {@code "vespa.test.config"} is set (to a file path), a file at that location
+ * is attempted read, and config parsed from it.
+ * Otherwise, config is fetched over HTTP from the hosted Vespa API, assuming the deployment indicated
+ * by the optional {@code "environment"} and {@code "region"} system properties exists.
+ * When environment is not specified, it defaults to {@link Environment#dev},
+ * while region must be set unless the environment is {@link Environment#dev} or {@link Environment#perf}.
+ */
+ public static synchronized TestRuntime get() {
+ if (theRuntime == null) {
+ String configPath = System.getProperty("vespa.test.config");
+ Authenticator authenticator = new ai.vespa.hosted.auth.Authenticator();
+ theRuntime = new TestRuntime(configPath != null ? fromFile(configPath) : fromController(authenticator),
+ authenticator);
+ }
+ return theRuntime;
+ }
+
+ /** Returns a copy of this runtime, with the given authenticator. */
+ public TestRuntime with(Authenticator authenticator) {
+ return new TestRuntime(config, authenticator);
+ }
+
+ private static TestConfig fromFile(String path) {
+ try {
+ return TestConfig.fromJson(Files.readAllBytes(Paths.get(path)));
+ }
+ catch (Exception e) {
+ throw new IllegalArgumentException("Failed reading config from '" + path + "'!", e);
+ }
+ }
+
+ private static TestConfig fromController(Authenticator authenticator) {
+ ControllerHttpClient controller = authenticator.controller();
+ ApplicationId id = Properties.application();
+ Environment environment = Properties.environment().orElse(Environment.dev);
+ ZoneId zone = Properties.region().map(region -> ZoneId.from(environment, region))
+ .orElseGet(() -> controller.defaultZone(environment));
+ return controller.testConfig(id, zone);
+ }
+
+}
diff --git a/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpDeployment.java b/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpDeployment.java
index 8eebe04ebef..6234b54c0a1 100644
--- a/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpDeployment.java
+++ b/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpDeployment.java
@@ -1,9 +1,13 @@
package ai.vespa.hosted.cd.http;
+import ai.vespa.hosted.api.Authenticator;
import ai.vespa.hosted.cd.Deployment;
import ai.vespa.hosted.cd.Endpoint;
import ai.vespa.hosted.cd.TestDeployment;
-import ai.vespa.hosted.cd.TestEndpoint;
+
+import java.net.URI;
+import java.util.Map;
+import java.util.stream.Collectors;
/**
* A remote deployment of a Vespa application, reachable over HTTP. Contains {@link HttpEndpoint}s.
@@ -12,6 +16,15 @@ import ai.vespa.hosted.cd.TestEndpoint;
*/
public class HttpDeployment implements Deployment {
+ private final Map<String, HttpEndpoint> endpoints;
+
+ /** Creates a representation of the given deployment endpoints, using the authenticator for data plane access. */
+ public HttpDeployment(Map<String, URI> endpoints, Authenticator authenticator) {
+ this.endpoints = endpoints.entrySet().stream()
+ .collect(Collectors.toUnmodifiableMap(entry -> entry.getKey(),
+ entry -> new HttpEndpoint(entry.getValue(), authenticator)));
+ }
+
@Override
public Endpoint endpoint() {
return null;
diff --git a/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpEndpoint.java b/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpEndpoint.java
index 4fafa65773d..798eb1e692b 100644
--- a/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpEndpoint.java
+++ b/tenant-cd/src/main/java/ai/vespa/hosted/cd/http/HttpEndpoint.java
@@ -1,6 +1,6 @@
package ai.vespa.hosted.cd.http;
-import ai.vespa.hosted.auth.Authenticator;
+import ai.vespa.hosted.api.Authenticator;
import com.yahoo.slime.Inspector;
import com.yahoo.slime.JsonDecoder;
import com.yahoo.slime.Slime;
@@ -34,11 +34,11 @@ public class HttpEndpoint implements TestEndpoint {
private final URI endpoint;
private final HttpClient client;
- private final Authenticator authenticator;
+ private final ai.vespa.hosted.api.Authenticator authenticator;
- public HttpEndpoint(URI endpoint) {
+ public HttpEndpoint(URI endpoint, Authenticator authenticator) {
this.endpoint = requireNonNull(endpoint);
- this.authenticator = new Authenticator();
+ this.authenticator = requireNonNull(authenticator);
this.client = HttpClient.newBuilder()
.sslContext(authenticator.sslContext())
.connectTimeout(Duration.ofSeconds(5))