diff --git a/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java b/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java index 7146df15b53..72830db475e 100644 --- a/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java +++ b/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationBuilder.java @@ -558,33 +558,6 @@ private static void loadJmxMetricsEnvVar( } } - private static void addDefaultJmxMetricsIfNotPresent(Configuration config) { - if (!jmxMetricExists(config.jmxMetrics, "java.lang:type=Threading", "ThreadCount")) { - JmxMetric threadCountJmxMetric = new JmxMetric(); - threadCountJmxMetric.name = "Current Thread Count"; - threadCountJmxMetric.objectName = "java.lang:type=Threading"; - threadCountJmxMetric.attribute = "ThreadCount"; - config.jmxMetrics.add(threadCountJmxMetric); - } - if (!jmxMetricExists(config.jmxMetrics, "java.lang:type=ClassLoading", "LoadedClassCount")) { - JmxMetric classCountJmxMetric = new JmxMetric(); - classCountJmxMetric.name = "Loaded Class Count"; - classCountJmxMetric.objectName = "java.lang:type=ClassLoading"; - classCountJmxMetric.attribute = "LoadedClassCount"; - config.jmxMetrics.add(classCountJmxMetric); - } - } - - private static boolean jmxMetricExists( - List jmxMetrics, String objectName, String attribute) { - for (JmxMetric metric : jmxMetrics) { - if (metric.objectName.equals(objectName) && metric.attribute.equals(attribute)) { - return true; - } - } - return false; - } - private static void overlayInstrumentationEnabledEnvVars( Configuration config, Function envVarsFunction) { config.instrumentation.azureSdk.enabled = @@ -844,7 +817,6 @@ static void overlayFromEnv( loadLogCaptureEnvVar(config, envVarsFunction); loadJmxMetricsEnvVar(config, envVarsFunction); - addDefaultJmxMetricsIfNotPresent(config); overlayProfilerEnvVars(config, envVarsFunction); overlayAadEnvVars(config, envVarsFunction); overlayInstrumentationEnabledEnvVars(config, envVarsFunction); diff --git a/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/init/PerformanceCounterInitializer.java b/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/init/PerformanceCounterInitializer.java index 25a656c58e0..a17fb4485cd 100644 --- a/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/init/PerformanceCounterInitializer.java +++ b/agent/agent-tooling/src/main/java/com/microsoft/applicationinsights/agent/internal/init/PerformanceCounterInitializer.java @@ -13,6 +13,7 @@ import com.microsoft.applicationinsights.agent.internal.perfcounter.GcPerformanceCounter; import com.microsoft.applicationinsights.agent.internal.perfcounter.JmxAttributeData; import com.microsoft.applicationinsights.agent.internal.perfcounter.JmxDataFetcher; +import com.microsoft.applicationinsights.agent.internal.perfcounter.JmxMetricPerformanceCounter; import com.microsoft.applicationinsights.agent.internal.perfcounter.JvmHeapMemoryUsedPerformanceCounter; import com.microsoft.applicationinsights.agent.internal.perfcounter.OshiPerformanceCounter; import com.microsoft.applicationinsights.agent.internal.perfcounter.PerformanceCounterContainer; @@ -25,6 +26,7 @@ import java.lang.management.ManagementFactory; import java.lang.management.ThreadMXBean; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collection; import java.util.HashMap; import java.util.List; @@ -48,6 +50,21 @@ public static void initialize(Configuration configuration) { PerformanceCounterContainer.INSTANCE.setLogAvailableJmxMetrics(); } + // We don't want these two to be flowing to the OTLP endpoint + // because in the long term we will probably be deprecating these + // in favor of the otel instrumentation runtime metrics that relay + // the same information. + registerCounterInContainer( + "java.lang:type=Threading", + "Current Thread Count", + "ThreadCount", + configuration.jmxMetrics); + registerCounterInContainer( + "java.lang:type=ClassLoading", + "Loaded Class Count", + "LoadedClassCount", + configuration.jmxMetrics); + loadCustomJmxPerfCounters(configuration.jmxMetrics); PerformanceCounterContainer.INSTANCE.register( @@ -74,6 +91,29 @@ private static boolean isAgentRunningInSandboxEnvWindows() { return qualifiedSdkVersion.startsWith("awr") || qualifiedSdkVersion.startsWith("fwr"); } + private static void registerCounterInContainer( + String objectName, + String metricName, + String attribute, + List jmxMetricsList) { + if (!isMetricInConfig(objectName, attribute, jmxMetricsList)) { + JmxAttributeData attributeData = new JmxAttributeData(metricName, attribute); + JmxMetricPerformanceCounter jmxPerfCounter = + new JmxMetricPerformanceCounter(objectName, Arrays.asList(attributeData)); + PerformanceCounterContainer.INSTANCE.register(jmxPerfCounter); + } + } + + private static boolean isMetricInConfig( + String objectName, String attribute, List jmxMetricsList) { + for (Configuration.JmxMetric metric : jmxMetricsList) { + if (metric.objectName.equals(objectName) && metric.attribute.equals(attribute)) { + return true; + } + } + return false; + } + /** * The method will load the Jmx performance counters requested by the user to the system: 1. Build * a map where the key is the Jmx object name and the value is a list of requested attributes. 2. diff --git a/agent/agent-tooling/src/test/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationTest.java b/agent/agent-tooling/src/test/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationTest.java index ea78b17ce43..abdf8d762b8 100644 --- a/agent/agent-tooling/src/test/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationTest.java +++ b/agent/agent-tooling/src/test/java/com/microsoft/applicationinsights/agent/internal/configuration/ConfigurationTest.java @@ -99,12 +99,11 @@ void shouldParseFromEnvVar() throws IOException { List jmxMetrics = parseJmxMetricsJson(jmxMetricsJson); assertThat(jmxMetrics.size()).isEqualTo(2); - assertThat(configuration.jmxMetrics.size()).isEqualTo(3); + assertThat(configuration.jmxMetrics.size()).isEqualTo(2); assertThat(configuration.jmxMetrics.get(0).name) .isEqualTo(jmxMetrics.get(0).name); // class count is overridden by the env var assertThat(configuration.jmxMetrics.get(1).name) .isEqualTo(jmxMetrics.get(1).name); // code cache is overridden by the env var - assertThat("Current Thread Count").isEqualTo(configuration.jmxMetrics.get(2).name); } @Test @@ -513,12 +512,11 @@ void shouldOverrideJmxMetrics() throws IOException { List jmxMetrics = parseJmxMetricsJson(jmxMetricsJson); assertThat(jmxMetrics.size()).isEqualTo(2); - assertThat(configuration.jmxMetrics.size()).isEqualTo(3); + assertThat(configuration.jmxMetrics.size()).isEqualTo(2); assertThat(configuration.jmxMetrics.get(0).name) .isEqualTo(jmxMetrics.get(0).name); // class count is overridden by the env var assertThat(configuration.jmxMetrics.get(1).name) .isEqualTo(jmxMetrics.get(1).name); // code cache is overridden by the env var - assertThat("Current Thread Count").isEqualTo(configuration.jmxMetrics.get(2).name); } @Test diff --git a/smoke-tests/apps/DetectUnexpectedOtelMetrics/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/DetectUnexpectedOtelMetricsTest.java b/smoke-tests/apps/DetectUnexpectedOtelMetrics/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/DetectUnexpectedOtelMetricsTest.java index 41fc0b52042..dfd6714a67c 100644 --- a/smoke-tests/apps/DetectUnexpectedOtelMetrics/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/DetectUnexpectedOtelMetricsTest.java +++ b/smoke-tests/apps/DetectUnexpectedOtelMetrics/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/DetectUnexpectedOtelMetricsTest.java @@ -43,6 +43,7 @@ abstract class DetectUnexpectedOtelMetricsTest { EXPECTED_METRIC_NAMES.add("% Of Max Heap Memory Used"); EXPECTED_METRIC_NAMES.add("GC Total Count"); EXPECTED_METRIC_NAMES.add("GC Total Time"); + EXPECTED_METRIC_NAMES.add("http.server.request.duration"); EXPECTED_METRIC_NAMES.add("http.client.request.duration"); } diff --git a/smoke-tests/apps/JmxMetric/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JmxMetricTest.java b/smoke-tests/apps/JmxMetric/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JmxMetricTest.java index c170dcd8d03..b772597b902 100644 --- a/smoke-tests/apps/JmxMetric/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JmxMetricTest.java +++ b/smoke-tests/apps/JmxMetric/src/smokeTest/java/com/microsoft/applicationinsights/smoketest/JmxMetricTest.java @@ -52,13 +52,9 @@ abstract class JmxMetricTest { *

- Higher than Java 8: G1 Young Generation,type=GarbageCollector, G1 Old * Generation,type=GarbageCollector. (the corrresponding metric names are GCYoung and GCOld) * - *

- Loaded_Class_Count: This covers the case of collecting a default jmx metric that the - * customer did not specify in applicationInsights.json. Also note that there are underscores - * instead of spaces, as we are emitting the metric via OpenTelemetry now. We intend to implement - * a change in azure-sdk-for-java repo to have the metrics still emit with spaces to Breeze, but - * the OTEL collector will still get the metric names with _. When that change gets merged & - * incorporated, we will need to change this/DetectUnexpectedOtelMetrics test so that the Breeze - * verification expects our default jmx metrics with spaces. + *

- Loaded Class Count: This covers the case of collecting a default jmx metric that the + * customer did not specify in applicationInsights.json. TODO deprecate this in favor of analogous + * metric that is emitted via OTel instrumentation runtime metrics. * *

- BooleanJmxMetric: This covers the case of a jmx metric attribute with a boolean value. * @@ -81,7 +77,6 @@ abstract class JmxMetricTest { "NameWithDot", "DefaultJmxMetricNameOverride", "WildcardJmxMetric", - "Loaded_Class_Count", "BooleanJmxMetric", "DotInAttributeNameAsPathSeparator")); @@ -91,8 +86,8 @@ abstract class JmxMetricTest { @Test @TargetUri("/test") void doMostBasicTest() throws Exception { - verifyJmxMetricsSentToBreeze(); verifyJmxMetricsSentToOtlpEndpoint(); + verifyJmxMetricsSentToBreeze(); } @SuppressWarnings({"PreferJavaTimeOverload"}) @@ -126,12 +121,9 @@ private void verifyJmxMetricsSentToOtlpEndpoint() { } } - for (Map.Entry entry : occurrences.entrySet()) { - System.out.println(entry.toString()); - } // confirm that those metrics received once or twice // (the collector seems to run for 5-10 sec) - assertThat(occurrences.keySet()).hasSize(6); + assertThat(occurrences.keySet()).hasSize(jmxMetricsAllJavaVersionsOtlp.size()); for (int value : occurrences.values()) { assertThat(value).isBetween(1, 8); } @@ -140,7 +132,7 @@ private void verifyJmxMetricsSentToOtlpEndpoint() { private void verifyJmxMetricsSentToBreeze() throws Exception { List metricItems = - testing.mockedIngestion.waitForItems(JmxMetricTest::isJmxMetric, 1, 10, TimeUnit.SECONDS); + testing.mockedIngestion.waitForItems(JmxMetricTest::isJmxMetric, 7, 10, TimeUnit.SECONDS); assertThat(metricItems).hasSizeBetween(7, 16);