diff options
Diffstat (limited to 'container-core/src/test/java')
9 files changed, 623 insertions, 28 deletions
diff --git a/container-core/src/test/java/ai/vespa/cloud/SystemInfoTest.java b/container-core/src/test/java/ai/vespa/cloud/SystemInfoTest.java new file mode 100644 index 00000000000..6bc8b395e00 --- /dev/null +++ b/container-core/src/test/java/ai/vespa/cloud/SystemInfoTest.java @@ -0,0 +1,49 @@ +// Copyright Verizon Media. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package ai.vespa.cloud; + +import org.junit.Test; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.fail; + +/** + * @author bratseth + */ +public class SystemInfoTest { + + @Test + public void testSystemInfo() { + Zone zone = new Zone(Environment.dev, "us-west-1"); + SystemInfo info = new SystemInfo(zone); + assertEquals(zone, info.zone()); + } + + @Test + public void testZone() { + Zone zone = Zone.from("dev.us-west-1"); + zone = Zone.from(zone.toString()); + assertEquals(Environment.dev, zone.environment()); + assertEquals("us-west-1", zone.region()); + Zone sameZone = Zone.from("dev.us-west-1"); + assertEquals(sameZone.hashCode(), zone.hashCode()); + assertEquals(sameZone, zone); + + try { + Zone.from("invalid"); + fail("Expected exception"); + } + catch (IllegalArgumentException e) { + assertEquals("A zone string must be on the form [environment].[region], but was 'invalid'", + e.getMessage()); + } + + try { + Zone.from("invalid.us-west-1"); + fail("Expected exception"); + } + catch (IllegalArgumentException e) { + assertEquals("Invalid zone 'invalid.us-west-1': No environment named 'invalid'", e.getMessage()); + } + } + +} diff --git a/container-core/src/test/java/com/yahoo/container/core/config/BundleManagerTest.java b/container-core/src/test/java/com/yahoo/container/core/config/BundleManagerTest.java new file mode 100644 index 00000000000..414e6b05128 --- /dev/null +++ b/container-core/src/test/java/com/yahoo/container/core/config/BundleManagerTest.java @@ -0,0 +1,106 @@ +// Copyright 2020 Oath Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.container.core.config; + +import com.yahoo.config.FileReference; +import org.junit.Before; +import org.junit.Test; +import org.osgi.framework.Bundle; + +import java.util.List; +import java.util.Map; +import java.util.Set; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertTrue; + +/** + * @author gjoranv + */ +public class BundleManagerTest { + + private static final FileReference BUNDLE_1_REF = new FileReference("bundle-1"); + private static final Bundle BUNDLE_1 = new TestBundle(BUNDLE_1_REF.value()); + private static final FileReference BUNDLE_2_REF = new FileReference("bundle-2"); + private static final Bundle BUNDLE_2 = new TestBundle(BUNDLE_2_REF.value()); + + private BundleManager bundleLoader; + private TestOsgi osgi; + + @Before + public void setup() { + osgi = new TestOsgi(testBundles()); + var bundleInstaller = new TestBundleInstaller(); + bundleLoader = new BundleManager(osgi); + bundleLoader.useCustomBundleInstaller(bundleInstaller); + } + + @Test + public void bundles_are_installed_and_started() { + bundleLoader.use(List.of(BUNDLE_1_REF)); + assertEquals(1, osgi.getInstalledBundles().size()); + + // The bundle is installed and started + TestBundle installedBundle = (TestBundle)osgi.getInstalledBundles().get(0); + assertEquals(BUNDLE_1.getSymbolicName(), installedBundle.getSymbolicName()); + assertTrue(installedBundle.started); + + // The file reference is active + assertEquals(1, bundleLoader.getActiveFileReferences().size()); + assertEquals(BUNDLE_1_REF, bundleLoader.getActiveFileReferences().get(0)); + } + + @Test + public void new_bundle_can_be_installed_in_reconfig() { + bundleLoader.use(List.of(BUNDLE_1_REF)); + Set<Bundle> obsoleteBundles = bundleLoader.use(List.of(BUNDLE_1_REF, BUNDLE_2_REF)); + + // No bundles are obsolete + assertTrue(obsoleteBundles.isEmpty()); + + // Both bundles are installed + assertEquals(2, osgi.getInstalledBundles().size()); + assertEquals(BUNDLE_1.getSymbolicName(), osgi.getInstalledBundles().get(0).getSymbolicName()); + assertEquals(BUNDLE_2.getSymbolicName(), osgi.getInstalledBundles().get(1).getSymbolicName()); + + // Both bundles are current + assertEquals(2, osgi.getCurrentBundles().size()); + assertEquals(BUNDLE_1.getSymbolicName(), osgi.getCurrentBundles().get(0).getSymbolicName()); + assertEquals(BUNDLE_2.getSymbolicName(), osgi.getCurrentBundles().get(1).getSymbolicName()); + + + // Both file references are active + assertEquals(2, bundleLoader.getActiveFileReferences().size()); + assertEquals(BUNDLE_1_REF, bundleLoader.getActiveFileReferences().get(0)); + assertEquals(BUNDLE_2_REF, bundleLoader.getActiveFileReferences().get(1)); + } + + @Test + public void unused_bundle_is_marked_obsolete_after_reconfig() { + bundleLoader.use(List.of(BUNDLE_1_REF)); + Set<Bundle> obsoleteBundles = bundleLoader.use(List.of(BUNDLE_2_REF)); + + // The returned set of obsolete bundles contains bundle-1 + assertEquals(1, obsoleteBundles.size()); + assertEquals(BUNDLE_1.getSymbolicName(), obsoleteBundles.iterator().next().getSymbolicName()); + + // Both bundles are installed + assertEquals(2, osgi.getInstalledBundles().size()); + assertEquals(BUNDLE_1.getSymbolicName(), osgi.getInstalledBundles().get(0).getSymbolicName()); + assertEquals(BUNDLE_2.getSymbolicName(), osgi.getInstalledBundles().get(1).getSymbolicName()); + + // Only bundle-2 is current + assertEquals(1, osgi.getCurrentBundles().size()); + assertEquals(BUNDLE_2.getSymbolicName(), osgi.getCurrentBundles().get(0).getSymbolicName()); + + // Only the bundle-2 file reference is active + assertEquals(1, bundleLoader.getActiveFileReferences().size()); + assertEquals(BUNDLE_2_REF, bundleLoader.getActiveFileReferences().get(0)); + } + + + private static Map<String, Bundle> testBundles() { + return Map.of(BUNDLE_1_REF.value(), BUNDLE_1, + BUNDLE_2_REF.value(), BUNDLE_2); + } + +} diff --git a/container-core/src/test/java/com/yahoo/container/core/config/TestBundle.java b/container-core/src/test/java/com/yahoo/container/core/config/TestBundle.java new file mode 100644 index 00000000000..421f4302c27 --- /dev/null +++ b/container-core/src/test/java/com/yahoo/container/core/config/TestBundle.java @@ -0,0 +1,102 @@ +// Copyright 2020 Oath Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.container.core.config; + +import com.yahoo.container.bundle.MockBundle; +import org.osgi.framework.Bundle; +import org.osgi.framework.Version; +import org.osgi.framework.wiring.BundleCapability; +import org.osgi.framework.wiring.BundleRequirement; +import org.osgi.framework.wiring.BundleRevision; +import org.osgi.framework.wiring.BundleWiring; +import org.osgi.resource.Capability; +import org.osgi.resource.Requirement; + +import java.util.List; + +/** + * @author gjoranv + */ +class TestBundle extends MockBundle { + + private static final BundleRevision revision = new TestBundleRevision(); + + private final String symbolicName; + + boolean started = false; + + TestBundle(String symbolicName) { + this.symbolicName = symbolicName; + } + + @Override + public void start() { + started = true; + } + + @Override + public String getSymbolicName() { + return symbolicName; + } + + + @SuppressWarnings("unchecked") + @Override + public <T> T adapt(Class<T> type) { + if (type.equals(BundleRevision.class)) { + return (T) revision; + } else { + throw new UnsupportedOperationException(); + } + } + + + static class TestBundleRevision implements BundleRevision { + + // Ensure this is not seen as a fragment bundle. + @Override + public int getTypes() { + return 0; + } + + @Override + public String getSymbolicName() { + throw new UnsupportedOperationException(); + } + + @Override + public Version getVersion() { + throw new UnsupportedOperationException(); + } + + @Override + public List<BundleCapability> getDeclaredCapabilities(String namespace) { + throw new UnsupportedOperationException(); + } + + @Override + public List<BundleRequirement> getDeclaredRequirements(String namespace) { + throw new UnsupportedOperationException(); + } + + @Override + public BundleWiring getWiring() { + throw new UnsupportedOperationException(); + } + + @Override + public List<Capability> getCapabilities(String namespace) { + throw new UnsupportedOperationException(); + } + + @Override + public List<Requirement> getRequirements(String namespace) { + throw new UnsupportedOperationException(); + } + + @Override + public Bundle getBundle() { + throw new UnsupportedOperationException(); + } + } + +} diff --git a/container-core/src/test/java/com/yahoo/container/core/config/TestBundleInstaller.java b/container-core/src/test/java/com/yahoo/container/core/config/TestBundleInstaller.java new file mode 100644 index 00000000000..43a5268eabf --- /dev/null +++ b/container-core/src/test/java/com/yahoo/container/core/config/TestBundleInstaller.java @@ -0,0 +1,20 @@ +// Copyright 2020 Oath Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.container.core.config; + +import com.yahoo.config.FileReference; +import com.yahoo.osgi.Osgi; +import org.osgi.framework.Bundle; + +import java.util.List; + +/** + * @author gjoranv + */ +class TestBundleInstaller implements BundleInstaller { + + @Override + public List<Bundle> installBundles(FileReference reference, Osgi osgi) { + return osgi.install(reference.value()); + } + +} diff --git a/container-core/src/test/java/com/yahoo/container/core/config/TestOsgi.java b/container-core/src/test/java/com/yahoo/container/core/config/TestOsgi.java new file mode 100644 index 00000000000..54a3159239c --- /dev/null +++ b/container-core/src/test/java/com/yahoo/container/core/config/TestOsgi.java @@ -0,0 +1,57 @@ +// Copyright 2020 Oath Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.container.core.config; + +import com.yahoo.osgi.MockOsgi; +import org.osgi.framework.Bundle; + +import java.util.ArrayList; +import java.util.Collection; +import java.util.List; +import java.util.Map; + +/** + * @author gjoranv + */ +class TestOsgi extends MockOsgi { + + private final Map<String, Bundle> availableBundles; + + private final List<Bundle> installedBundles = new ArrayList<>(); + private final List<Bundle> allowedDuplicates = new ArrayList<>(); + + TestOsgi(Map<String, Bundle> availableBundles) { + this.availableBundles = availableBundles; + } + + @Override + public List<Bundle> install(String fileReferenceValue) { + if (! availableBundles.containsKey(fileReferenceValue)) + throw new IllegalArgumentException("No such bundle: " + fileReferenceValue); + + Bundle bundle = availableBundles.get(fileReferenceValue); + installedBundles.add(bundle); + return List.of(bundle); + } + + @Override + public Bundle[] getBundles() { + return installedBundles.toArray(new Bundle[0]); + } + + public List<Bundle> getInstalledBundles() { + return installedBundles; + } + + @Override + public List<Bundle> getCurrentBundles() { + var currentBundles = new ArrayList<>(installedBundles); + currentBundles.removeAll(allowedDuplicates); + return currentBundles; + } + + @Override + public void allowDuplicateBundles(Collection<Bundle> bundles) { + allowedDuplicates.addAll(bundles); + } + +} diff --git a/container-core/src/test/java/com/yahoo/container/handler/VipStatusTestCase.java b/container-core/src/test/java/com/yahoo/container/handler/VipStatusTestCase.java index 52679c15957..e13debcddda 100644 --- a/container-core/src/test/java/com/yahoo/container/handler/VipStatusTestCase.java +++ b/container-core/src/test/java/com/yahoo/container/handler/VipStatusTestCase.java @@ -4,6 +4,9 @@ package com.yahoo.container.handler; import static org.junit.Assert.*; import com.yahoo.container.QrSearchersConfig; +import com.yahoo.container.core.VipStatusConfig; +import com.yahoo.container.jdisc.state.StateMonitor; +import com.yahoo.jdisc.core.SystemTimer; import org.junit.Test; /** @@ -13,44 +16,101 @@ import org.junit.Test; */ public class VipStatusTestCase { - @Test - public void testVipStatusWorksWithClusters() { + private static QrSearchersConfig getSearchersConfig(String[] clusters) { var b = new QrSearchersConfig.Builder(); - var searchClusterB = new QrSearchersConfig.Searchcluster.Builder(); - searchClusterB.name("cluster1"); - searchClusterB.name("cluster2"); - searchClusterB.name("cluster3"); - b.searchcluster(searchClusterB); - VipStatus v = new VipStatus(b.build()); + if (clusters.length > 0) { + var searchClusterB = new QrSearchersConfig.Searchcluster.Builder(); + for (String cluster : clusters) { + searchClusterB.name(cluster); + } + b.searchcluster(searchClusterB); + } + return b.build(); + } + + private static VipStatus getVipStatus(String[] clusters, StateMonitor.Status startState, boolean initiallyInRotation) { + return new VipStatus(getSearchersConfig(clusters), + new VipStatusConfig.Builder().initiallyInRotation(initiallyInRotation).build(), + new ClustersStatus(), + new StateMonitor(1000, startState, new SystemTimer(), runnable -> { + Thread thread = new Thread(runnable, "StateMonitor"); + thread.setDaemon(true); + return thread; + })); + } - String cluster1 = "cluster1"; - String cluster2 = "cluster2"; - String cluster3 = "cluster3"; + private static void remove(String[] clusters, VipStatus v) { + for (String s : clusters) { + v.removeFromRotation(s); + } + } + + private static void add(String[] clusters, VipStatus v) { + for (String s : clusters) { + v.addToRotation(s); + } + } + private static void verifyUpOrDown(String[] clusters, StateMonitor.Status status) { + VipStatus v = getVipStatus(clusters, status, true); + remove(clusters, v); // initial state assertFalse(v.isInRotation()); + v.addToRotation(clusters[0]); + assertFalse(v.isInRotation()); + v.addToRotation(clusters[1]); + assertFalse(v.isInRotation()); + v.addToRotation(clusters[2]); + assertTrue(v.isInRotation()); + } + + @Test + public void testInitializingOrDownRequireAllUp() { + String[] clusters = {"cluster1", "cluster2", "cluster3"}; + verifyUpOrDown(clusters, StateMonitor.Status.initializing); + verifyUpOrDown(clusters, StateMonitor.Status.down); + } + + @Test + public void testUpRequireAllDown() { + String[] clusters = {"cluster1", "cluster2", "cluster3"}; - // one cluster becomes up - v.addToRotation(cluster1); + VipStatus v = getVipStatus(clusters, StateMonitor.Status.initializing, true); + assertFalse(v.isInRotation()); + add(clusters, v); assertTrue(v.isInRotation()); - // all clusters down - v.removeFromRotation(cluster1); - v.removeFromRotation(cluster2); - v.removeFromRotation(cluster3); + v.removeFromRotation(clusters[0]); + assertTrue(v.isInRotation()); + v.removeFromRotation(clusters[1]); + assertTrue(v.isInRotation()); + v.removeFromRotation(clusters[2]); + assertFalse(v.isInRotation()); // All down + v.addToRotation(clusters[1]); assertFalse(v.isInRotation()); - // some clusters down - v.addToRotation(cluster2); + v.addToRotation(clusters[0]); + v.addToRotation(clusters[2]); + assertTrue(v.isInRotation()); // All up + v.removeFromRotation(clusters[0]); + v.removeFromRotation(clusters[2]); assertTrue(v.isInRotation()); - // all clusters up - v.addToRotation(cluster1); - v.addToRotation(cluster3); + v.addToRotation(clusters[0]); + v.addToRotation(clusters[2]); assertTrue(v.isInRotation()); - // and down again - v.removeFromRotation(cluster1); - v.removeFromRotation(cluster2); - v.removeFromRotation(cluster3); + } + + @Test + public void testNoClustersConfiguringInitiallyInRotationFalse() { + String[] clusters = {}; + VipStatus v = getVipStatus(clusters, StateMonitor.Status.initializing, false); assertFalse(v.isInRotation()); } -} + @Test + public void testNoClustersConfiguringInitiallyInRotationTrue() { + String[] clusters = {}; + VipStatus v = getVipStatus(clusters, StateMonitor.Status.initializing, true); + assertTrue(v.isInRotation()); + } + +}
\ No newline at end of file diff --git a/container-core/src/test/java/com/yahoo/container/handler/metrics/MetricsV2HandlerTest.java b/container-core/src/test/java/com/yahoo/container/handler/metrics/MetricsV2HandlerTest.java new file mode 100644 index 00000000000..b57814e50aa --- /dev/null +++ b/container-core/src/test/java/com/yahoo/container/handler/metrics/MetricsV2HandlerTest.java @@ -0,0 +1,143 @@ +// Copyright 2019 Oath Inc. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.container.handler.metrics; + +import com.github.tomakehurst.wiremock.junit.WireMockRule; +import com.yahoo.container.jdisc.RequestHandlerTestDriver; +import org.json.JSONArray; +import org.json.JSONException; +import org.json.JSONObject; +import org.junit.Before; +import org.junit.Ignore; +import org.junit.Rule; +import org.junit.Test; + +import java.io.BufferedReader; +import java.io.InputStream; +import java.io.InputStreamReader; +import java.util.concurrent.Executors; +import java.util.stream.Collectors; + +import static com.github.tomakehurst.wiremock.client.WireMock.aResponse; +import static com.github.tomakehurst.wiremock.client.WireMock.equalTo; +import static com.github.tomakehurst.wiremock.client.WireMock.get; +import static com.github.tomakehurst.wiremock.client.WireMock.urlPathEqualTo; +import static com.github.tomakehurst.wiremock.core.WireMockConfiguration.options; +import static com.yahoo.container.handler.metrics.MetricsV2Handler.V2_PATH; +import static com.yahoo.container.handler.metrics.MetricsV2Handler.VALUES_PATH; +import static com.yahoo.container.handler.metrics.MetricsV2Handler.consumerQuery; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertTrue; +import static org.junit.Assert.fail; + +/** + * @author gjoranv + */ +public class MetricsV2HandlerTest { + + private static final String URI_BASE = "http://localhost"; + + private static final String V2_URI = URI_BASE + V2_PATH; + private static final String VALUES_URI = URI_BASE + VALUES_PATH; + + // Mock applicationmetrics api + private static final String MOCK_METRICS_PATH = "/node0"; + + private static final String TEST_FILE = "application-metrics.json"; + private static final String RESPONSE = getFileContents(TEST_FILE); + private static final String CPU_METRIC = "cpu.util"; + private static final String REPLACED_CPU_METRIC = "replaced_cpu_util"; + private static final String CUSTOM_CONSUMER = "custom-consumer"; + + private static RequestHandlerTestDriver testDriver; + + @Rule + public WireMockRule wireMockRule = new WireMockRule(options().dynamicPort()); + + @Before + public void setup() { + setupWireMock(); + var handler = new MetricsV2Handler(Executors.newSingleThreadExecutor(), + new MetricsProxyApiConfig.Builder() + .metricsPort(wireMockRule.port()) + .metricsApiPath(MOCK_METRICS_PATH) + .build()); + testDriver = new RequestHandlerTestDriver(handler); + } + + private void setupWireMock() { + wireMockRule.stubFor(get(urlPathEqualTo(MOCK_METRICS_PATH)) + .willReturn(aResponse().withBody(RESPONSE))); + + // Add a slightly different response for a custom consumer. + String myConsumerResponse = RESPONSE.replaceAll(CPU_METRIC, REPLACED_CPU_METRIC); + wireMockRule.stubFor(get(urlPathEqualTo(MOCK_METRICS_PATH)) + .withQueryParam("consumer", equalTo(CUSTOM_CONSUMER)) + .willReturn(aResponse().withBody(myConsumerResponse))); + } + + @Test + public void v2_response_contains_values_uri() throws Exception { + String response = testDriver.sendRequest(V2_URI).readAll(); + JSONObject root = new JSONObject(response); + assertTrue(root.has("resources")); + + JSONArray resources = root.getJSONArray("resources"); + assertEquals(1, resources.length()); + + JSONObject valuesUri = resources.getJSONObject(0); + assertEquals(VALUES_URI, valuesUri.getString("url")); + } + + @Ignore + @Test + public void visually_inspect_values_response() throws Exception { + JSONObject responseJson = getResponseAsJson(null); + System.out.println(responseJson.toString(4)); + } + + @Test + public void invalid_path_yields_error_response() throws Exception { + String response = testDriver.sendRequest(V2_URI + "/invalid").readAll(); + JSONObject root = new JSONObject(response); + assertTrue(root.has("error")); + assertTrue(root.getString("error" ).startsWith("No content")); + } + + @Test + public void values_response_is_equal_to_test_file() { + String response = testDriver.sendRequest(VALUES_URI).readAll(); + assertEquals(RESPONSE, response); + } + + @Test + public void consumer_is_propagated_to_metrics_proxy_api() throws JSONException { + JSONObject responseJson = getResponseAsJson(CUSTOM_CONSUMER); + + JSONObject firstNodeMetricsValues = + responseJson.getJSONArray("nodes").getJSONObject(0) + .getJSONObject("node") + .getJSONArray("metrics").getJSONObject(0) + .getJSONObject("values"); + + assertTrue(firstNodeMetricsValues.has(REPLACED_CPU_METRIC)); + } + + private JSONObject getResponseAsJson(String consumer) { + String response = testDriver.sendRequest(VALUES_URI + consumerQuery(consumer)).readAll(); + try { + return new JSONObject(response); + } catch (JSONException e) { + fail("Failed to create json object: " + e.getMessage()); + throw new RuntimeException(e); + } + } + + private static String getFileContents(String filename) { + InputStream in = MetricsV2HandlerTest.class.getClassLoader().getResourceAsStream(filename); + if (in == null) { + throw new RuntimeException("File not found: " + filename); + } + return new BufferedReader(new InputStreamReader(in)).lines().collect(Collectors.joining("\n")); + } + +} diff --git a/container-core/src/test/java/com/yahoo/container/jdisc/ThreadedHttpRequestHandlerTest.java b/container-core/src/test/java/com/yahoo/container/jdisc/ThreadedHttpRequestHandlerTest.java new file mode 100644 index 00000000000..07dba21e5b6 --- /dev/null +++ b/container-core/src/test/java/com/yahoo/container/jdisc/ThreadedHttpRequestHandlerTest.java @@ -0,0 +1,57 @@ +// Copyright Verizon Media. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.container.jdisc; + +import com.yahoo.jdisc.Metric; +import org.junit.Test; + +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.Executors; + +import static org.assertj.core.api.Assertions.assertThat; + +/** + * @author bjorncs + */ +public class ThreadedHttpRequestHandlerTest { + + @Test + public void unhandled_exceptions_metric_is_incremented_if_subclassed_handler_throws_exception() { + MetricMock metricMock = new MetricMock(); + ThreadedHttpRequestHandlerThrowingException handler = new ThreadedHttpRequestHandlerThrowingException(metricMock); + RequestHandlerTestDriver driver = new RequestHandlerTestDriver(handler); + + driver.sendRequest("http://localhost/myhandler"); + String expectedMetricName = "jdisc.http.handler.unhandled_exceptions"; + assertThat(metricMock.addInvocations) + .containsKey(expectedMetricName); + assertThat(metricMock.addInvocations.get(expectedMetricName).dimensions) + .containsEntry("exception", "DummyException"); + } + + private static class MetricMock implements Metric { + final ConcurrentHashMap<String, SimpleMetricContext> addInvocations = new ConcurrentHashMap<>(); + + @Override public void add(String key, Number val, Context ctx) { + addInvocations.put(key, (SimpleMetricContext)ctx); + } + @Override public void set(String key, Number val, Context ctx) {} + @Override public Context createContext(Map<String, ?> properties) { return new SimpleMetricContext(properties); } + } + + private static class SimpleMetricContext implements Metric.Context { + final Map<String, String> dimensions; + + @SuppressWarnings("unchecked") + SimpleMetricContext(Map<String, ?> dimensions) { this.dimensions = (Map<String, String>)dimensions; } + } + + private static class ThreadedHttpRequestHandlerThrowingException extends ThreadedHttpRequestHandler { + ThreadedHttpRequestHandlerThrowingException(Metric metric) { + super(Executors.newSingleThreadExecutor(), metric); + } + @Override public HttpResponse handle(HttpRequest request) { throw new DummyException(); } + } + + private static class DummyException extends RuntimeException {} +}
\ No newline at end of file diff --git a/container-core/src/test/java/com/yahoo/container/jdisc/state/StateHandlerTestBase.java b/container-core/src/test/java/com/yahoo/container/jdisc/state/StateHandlerTestBase.java index 78541137db5..8a1640e2c0e 100644 --- a/container-core/src/test/java/com/yahoo/container/jdisc/state/StateHandlerTestBase.java +++ b/container-core/src/test/java/com/yahoo/container/jdisc/state/StateHandlerTestBase.java @@ -57,7 +57,8 @@ public class StateHandlerTestBase { HealthMonitorConfig healthMonitorConfig = new HealthMonitorConfig( new HealthMonitorConfig.Builder() - .snapshot_interval(TimeUnit.MILLISECONDS.toSeconds(SNAPSHOT_INTERVAL))); + .snapshot_interval(TimeUnit.MILLISECONDS.toSeconds(SNAPSHOT_INTERVAL)) + .initialStatus("up")); ThreadFactory threadFactory = ignored -> mock(Thread.class); this.monitor = new StateMonitor(healthMonitorConfig, timer, threadFactory); builder.guiceModules().install(new AbstractModule() { |