This is an automated email from the ASF dual-hosted git repository. aldettinger pushed a commit to branch main in repository https://gitbox.apache.org/repos/asf/camel-quarkus.git
The following commit(s) were added to refs/heads/main by this push: new c5d367f457 Micrometer: Message History factory and JMX MicrometerMessageHistory is not covered (#5210) c5d367f457 is described below commit c5d367f4578ec7047f34f7a22278d9da020ff885 Author: James Netherton <jamesnether...@users.noreply.github.com> AuthorDate: Tue Aug 22 17:41:29 2023 +0100 Micrometer: Message History factory and JMX MicrometerMessageHistory is not covered (#5210) Fixes #5050 Co-authored-by: JiriOndrusek <ondrusek.j...@gmail.com> --- .../pages/reference/extensions/micrometer.adoc | 15 +++++-- .../runtime/src/main/doc/limitations.adoc | 10 ++++- .../micrometer/runtime/src/main/doc/usage.adoc | 2 +- integration-tests/micrometer/pom.xml | 4 ++ .../micrometer/it/MicrometerProducers.java | 6 +-- .../micrometer/it/MicrometerResource.java | 31 +++++++++++--- .../component/micrometer/it/MicrometerRoutes.java | 9 ++-- .../component/micrometer/it/MicrometerTest.java | 50 ++++++++++++++++++++-- .../it/NoMessageHistoryMicrometerTest.java | 36 ++++++++++++++++ .../micrometer/it/NoMessageHistoryProfile.java | 29 +++++++++++++ 10 files changed, 170 insertions(+), 22 deletions(-) diff --git a/docs/modules/ROOT/pages/reference/extensions/micrometer.adoc b/docs/modules/ROOT/pages/reference/extensions/micrometer.adoc index 6c220fca2b..70911002fd 100644 --- a/docs/modules/ROOT/pages/reference/extensions/micrometer.adoc +++ b/docs/modules/ROOT/pages/reference/extensions/micrometer.adoc @@ -58,22 +58,29 @@ Your application should declare the following dependency or one of the dependen </dependency> ---- -If no dependency is declared, the Micrometer extension creates a SimpleMeterRegistry instance, suitable mainly for testing. +If no dependency is declared, the Micrometer extension creates a `SimpleMeterRegistry` instance, suitable mainly for testing. [id="extensions-micrometer-camel-quarkus-limitations"] == Camel Quarkus limitations -[id="extensions-micrometer-limitations-exposing-micrometer-statisctics-in-jmx"] -=== Exposing Micrometer statisctics in JMX +[id="extensions-micrometer-limitations-exposing-micrometer-statistics-in-jmx"] +=== Exposing Micrometer statistics in JMX -The `Exposing Micrometer statisctics in JMX` action is not available in native mode as JMX is not supported on GraalVM. +Exposing Micrometer statistics in JMX is not available in native mode as `quarkus-micrometer-registry-jmx` does not +have native support at present. [id="extensions-micrometer-limitations-decrement-header-for-counter-is-ignored-by-prometheus"] === Decrement header for Counter is ignored by Prometheus Prometheus backend ignores negative values during increment of Counter metrics. +[id="extensions-micrometer-limitations-exposing-statistics-in-jmx"] +=== Exposing statistics in JMX === + +In {project-name}, registering a `JmxMeterRegistry` is simplified. Add a dependency for +`io.quarkiverse.micrometer.registry:quarkus-micrometer-registry-jmx` and a `JmxMeterRegistry` will automatically +get created for you. [id="extensions-micrometer-additional-camel-quarkus-configuration"] diff --git a/extensions/micrometer/runtime/src/main/doc/limitations.adoc b/extensions/micrometer/runtime/src/main/doc/limitations.adoc index 0b019beb5b..2edf56ebdb 100644 --- a/extensions/micrometer/runtime/src/main/doc/limitations.adoc +++ b/extensions/micrometer/runtime/src/main/doc/limitations.adoc @@ -1,8 +1,14 @@ -=== Exposing Micrometer statisctics in JMX +=== Exposing Micrometer statistics in JMX -The `Exposing Micrometer statisctics in JMX` action is not available in native mode as JMX is not supported on GraalVM. +Exposing Micrometer statistics in JMX is not available in native mode as `quarkus-micrometer-registry-jmx` does not +have native support at present. === Decrement header for Counter is ignored by Prometheus Prometheus backend ignores negative values during increment of Counter metrics. +=== Exposing statistics in JMX === + +In {project-name}, registering a `JmxMeterRegistry` is simplified. Add a dependency for +`io.quarkiverse.micrometer.registry:quarkus-micrometer-registry-jmx` and a `JmxMeterRegistry` will automatically +get created for you. diff --git a/extensions/micrometer/runtime/src/main/doc/usage.adoc b/extensions/micrometer/runtime/src/main/doc/usage.adoc index e4d485e32f..4d6a2b4d7a 100644 --- a/extensions/micrometer/runtime/src/main/doc/usage.adoc +++ b/extensions/micrometer/runtime/src/main/doc/usage.adoc @@ -10,4 +10,4 @@ Your application should declare the following dependency or one of the dependen </dependency> ---- -If no dependency is declared, the Micrometer extension creates a SimpleMeterRegistry instance, suitable mainly for testing. \ No newline at end of file +If no dependency is declared, the Micrometer extension creates a `SimpleMeterRegistry` instance, suitable mainly for testing. diff --git a/integration-tests/micrometer/pom.xml b/integration-tests/micrometer/pom.xml index fb156d5de7..92da57b5a1 100644 --- a/integration-tests/micrometer/pom.xml +++ b/integration-tests/micrometer/pom.xml @@ -47,6 +47,10 @@ <groupId>org.apache.camel.quarkus</groupId> <artifactId>camel-quarkus-bean</artifactId> </dependency> + <dependency> + <groupId>org.apache.camel.quarkus</groupId> + <artifactId>camel-quarkus-management</artifactId> + </dependency> <dependency> <groupId>io.micrometer</groupId> <artifactId>micrometer-registry-prometheus</artifactId> diff --git a/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerProducers.java b/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerProducers.java index 3d64957055..a4779e71ed 100644 --- a/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerProducers.java +++ b/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerProducers.java @@ -16,7 +16,7 @@ */ package org.apache.camel.quarkus.component.micrometer.it; -import java.util.Arrays; +import java.util.List; import io.micrometer.core.instrument.Clock; import io.micrometer.core.instrument.Meter; @@ -40,7 +40,7 @@ public class MicrometerProducers { @Produces @Singleton @IfBuildProfile("test") - public MeterRegistry registry(Clock clock) { + public MeterRegistry registry() { return new JmxMeterRegistry(CamelJmxConfig.DEFAULT, Clock.SYSTEM, HierarchicalNameMapper.DEFAULT); } @@ -48,7 +48,7 @@ public class MicrometerProducers { @Singleton @MeterFilterConstraint(applyTo = PrometheusMeterRegistry.class) public MeterFilter configurePrometheusRegistries() { - return MeterFilter.commonTags(Arrays.asList( + return MeterFilter.commonTags(List.of( Tag.of("customTag", "prometheus"))); } diff --git a/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerResource.java b/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerResource.java index b82a5c0917..fd7906e808 100644 --- a/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerResource.java +++ b/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerResource.java @@ -21,7 +21,6 @@ import java.util.LinkedList; import java.util.List; import java.util.NoSuchElementException; import java.util.concurrent.TimeUnit; -import java.util.stream.Collectors; import io.micrometer.core.instrument.MeterRegistry; import io.micrometer.core.instrument.Tag; @@ -42,6 +41,7 @@ import org.apache.camel.ProducerTemplate; import org.apache.camel.component.micrometer.MicrometerComponent; import org.apache.camel.component.micrometer.MicrometerConstants; import org.apache.camel.component.micrometer.eventnotifier.MicrometerEventNotifierService; +import org.apache.camel.component.micrometer.messagehistory.MicrometerMessageHistoryService; @Path("/micrometer") public class MicrometerResource { @@ -139,10 +139,7 @@ public class MicrometerResource { producerTemplate.sendBodyAndHeader(path, null, MicrometerConstants.HEADER_COUNTER_INCREMENT, increment); } else if (increment < 0) { producerTemplate.sendBodyAndHeader(path, null, MicrometerConstants.HEADER_COUNTER_DECREMENT, - 0 - increment); - List l = meterRegistry.getMeters().stream().filter(m -> m.getId().getName().contains("executor")) - .collect(Collectors.toList());//forEach(System.out::println); - System.out.println(l); + -increment); } else { producerTemplate.sendBody(path, null); } @@ -178,6 +175,17 @@ public class MicrometerResource { return Response.ok().entity(json).build(); } + @Path("/history") + @GET + public Response history() { + MicrometerMessageHistoryService service = camelContext.hasService(MicrometerMessageHistoryService.class); + if (service == null) { + return Response.status(500).entity("History is null").build(); + } + String json = service.dumpStatisticsAsJson(); + return Response.ok().entity(json).build(); + } + @Path("/annotations/call/{number}") @GET public Response annotationsCall(@PathParam("number") int number) { @@ -185,6 +193,19 @@ public class MicrometerResource { return Response.ok().build(); } + @Path("/getContextManagementName") + @GET + public Response getContextManagemetName() throws Exception { + return Response.ok().entity(camelContext.getManagementName()).build(); + } + + @Path("/sendJmxHistory") + @GET + public Response annotationsCall() { + producerTemplate.sendBody("direct:jmxHistory", "hello"); + return Response.ok().build(); + } + @Path("/gauge/{number}") @GET public Response gauge(@PathParam("number") int number) { diff --git a/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerRoutes.java b/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerRoutes.java index 5e4bba44b4..64d50941e3 100644 --- a/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerRoutes.java +++ b/integration-tests/micrometer/src/main/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerRoutes.java @@ -17,8 +17,7 @@ package org.apache.camel.quarkus.component.micrometer.it; import org.apache.camel.builder.RouteBuilder; - -import static org.apache.camel.component.micrometer.MicrometerConstants.HEADER_HISTOGRAM_VALUE; +import org.apache.camel.component.micrometer.MicrometerConstants; public class MicrometerRoutes extends RouteBuilder { @@ -34,7 +33,7 @@ public class MicrometerRoutes extends RouteBuilder { .to("micrometerCustom:counter:camel-quarkus-custom-counter"); from("direct:summary") - .setHeader(HEADER_HISTOGRAM_VALUE, simple("${body}")) + .setHeader(MicrometerConstants.HEADER_HISTOGRAM_VALUE, simple("${body}")) .to("micrometer:summary:camel-quarkus-summary"); from("direct:timer") @@ -52,5 +51,9 @@ public class MicrometerRoutes extends RouteBuilder { .otherwise().bean("testMetric", "call2") .end(); + from("direct:jmxHistory") + .id("jmxHistory") + .log("log: ${body}"); + } } diff --git a/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerTest.java b/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerTest.java index ccc6b4d31b..ac9b1f66e4 100644 --- a/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerTest.java +++ b/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/MicrometerTest.java @@ -78,7 +78,7 @@ class MicrometerTest extends AbstractMicrometerTest { .then() .statusCode(200); //component with Quarkus's registry should still see only 1 from the first call - assertEquals(1, getMetricValue(Integer.class, "counter", "camel-quarkus-custom-counter", null, 200, null)); + assertEquals(1, getMetricValue(Integer.class, "counter", "camel-quarkus-custom-counter")); //component with custom registry should be on 11 see only 1 from the first call assertEquals(11, getMetricValue(Integer.class, "counter", "camel-quarkus-custom-counter", null, 200, "custom")); } @@ -186,14 +186,14 @@ class MicrometerTest extends AbstractMicrometerTest { assertEquals(result.size(), 2); assertTrue(result.containsKey("camel.routes.running")); - assertEquals(7.0f, result.get("camel.routes.running")); + assertEquals(8.0f, result.get("camel.routes.running")); assertTrue(result.containsKey("camel.routes.added")); - assertEquals(7.0f, result.get("camel.routes.added")); + assertEquals(8.0f, result.get("camel.routes.added")); } @ParameterizedTest @ValueSource(strings = { "metrics", "org.apache.camel.micrometer" }) //test uses domains from both default and custom JMX registries - @DisabledOnIntegrationTest // JMX is not supported in native mode + @DisabledOnIntegrationTest("https://github.com/apache/camel-quarkus/issues/5209") public void testJMXQuarkusDomain(String domain) throws Exception { MBeanServer mBeanServer = ManagementFactory.getPlatformMBeanServer(); @@ -207,4 +207,46 @@ class MicrometerTest extends AbstractMicrometerTest { .getValue(); assertTrue(classes > 1); } + + @Test + @DisabledOnIntegrationTest("https://github.com/apache/camel-quarkus/issues/5209") + public void micrometerHistoryShouldBeAvailableThroughJMX() throws Exception { + //send a message to init history for the route with id `jmxHistory` + RestAssured.get("/micrometer/sendJmxHistory") + .then() + .statusCode(200); + + String contextManagementName = RestAssured.get("/micrometer/getContextManagementName") + .then() + .statusCode(200) + .extract().body().asString(); + + // get the message history service using JMX + String name = String.format("org.apache.camel:context=%s,type=services,name=MicrometerMessageHistoryService", + contextManagementName); + + MBeanServer mBeanServer = ManagementFactory.getPlatformMBeanServer(); + + ObjectName on = ObjectName.getInstance(name); + + //return json result + String json = (String) mBeanServer.invoke(on, "dumpStatisticsAsJson", null, null); + + assertTrue(json.contains("jmxHistory")); + + } + + @Test + public void micrometerHistoryShouldBeAvailableThroughCamelContext() throws Exception { + JsonPath jsonPath = RestAssured.get("/micrometer/history") + .then() + .statusCode(200) + .extract().jsonPath(); + + //assert that jason contains some history paths + assertNotNull(jsonPath.get("timers")); + assertNotNull(jsonPath.get("counters")); + assertNotNull(jsonPath.get("gauges")); + } + } diff --git a/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/NoMessageHistoryMicrometerTest.java b/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/NoMessageHistoryMicrometerTest.java new file mode 100644 index 0000000000..123e72c3a9 --- /dev/null +++ b/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/NoMessageHistoryMicrometerTest.java @@ -0,0 +1,36 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.camel.quarkus.component.micrometer.it; + +import io.quarkus.test.junit.QuarkusTest; +import io.quarkus.test.junit.TestProfile; +import io.restassured.RestAssured; +import org.hamcrest.Matchers; +import org.junit.jupiter.api.Test; + +@QuarkusTest +@TestProfile(NoMessageHistoryProfile.class) +class NoMessageHistoryMicrometerTest extends AbstractMicrometerTest { + + @Test + public void testNoHistory() { + RestAssured.get("/micrometer/history") + .then() + .statusCode(500) + .body(Matchers.is("History is null")); + } +} diff --git a/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/NoMessageHistoryProfile.java b/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/NoMessageHistoryProfile.java new file mode 100644 index 0000000000..6c9c6e7382 --- /dev/null +++ b/integration-tests/micrometer/src/test/java/org/apache/camel/quarkus/component/micrometer/it/NoMessageHistoryProfile.java @@ -0,0 +1,29 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.camel.quarkus.component.micrometer.it; + +import java.util.Map; + +import io.quarkus.test.junit.QuarkusTestProfile; + +public class NoMessageHistoryProfile implements QuarkusTestProfile { + + @Override + public Map<String, String> getConfigOverrides() { + return Map.of("quarkus.camel.metrics.enable-message-history", "false"); + } +}