From 72e2313fe84eed695e1e525722f0e05796c51cbb Mon Sep 17 00:00:00 2001 From: Andy Wilkinson Date: Fri, 5 Oct 2018 16:03:12 +0100 Subject: [PATCH] Polish "Auto-configure Micrometer's Jersey 2 server instrumentation" Closes gh-12482 --- .../JerseyServerMetricsAutoConfiguration.java | 58 ++++++++++++++----- .../server => jersey}/package-info.java | 4 +- .../server/JerseyServerMetricsProperties.java | 50 ---------------- .../main/resources/META-INF/spring.factories | 2 +- ...eyServerMetricsAutoConfigurationTests.java | 3 +- .../asciidoc/production-ready-features.adoc | 8 +-- 6 files changed, 52 insertions(+), 73 deletions(-) rename spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/{jersey2/server => jersey}/JerseyServerMetricsAutoConfiguration.java (62%) rename spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/{jersey2/server => jersey}/package-info.java (90%) delete mode 100644 spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsProperties.java rename spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/{jersey2/server => jersey}/JerseyServerMetricsAutoConfigurationTests.java (99%) diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsAutoConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfiguration.java similarity index 62% rename from spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsAutoConfiguration.java rename to spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfiguration.java index 431ec310d2..4a791db7b0 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsAutoConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfiguration.java @@ -14,12 +14,13 @@ * limitations under the License. */ -package org.springframework.boot.actuate.autoconfigure.metrics.jersey2.server; +package org.springframework.boot.actuate.autoconfigure.metrics.jersey; import java.lang.annotation.Annotation; import java.lang.reflect.AnnotatedElement; import io.micrometer.core.instrument.MeterRegistry; +import io.micrometer.core.instrument.config.MeterFilter; import io.micrometer.jersey2.server.AnnotationFinder; import io.micrometer.jersey2.server.DefaultJerseyTagsProvider; import io.micrometer.jersey2.server.JerseyTagsProvider; @@ -27,6 +28,9 @@ import io.micrometer.jersey2.server.MetricsApplicationEventListener; import org.glassfish.jersey.server.ResourceConfig; import org.springframework.boot.actuate.autoconfigure.metrics.MetricsAutoConfiguration; +import org.springframework.boot.actuate.autoconfigure.metrics.MetricsProperties; +import org.springframework.boot.actuate.autoconfigure.metrics.MetricsProperties.Web.Server; +import org.springframework.boot.actuate.autoconfigure.metrics.OnlyOnceLoggingDenyMeterFilter; import org.springframework.boot.actuate.autoconfigure.metrics.export.simple.SimpleMetricsExportAutoConfiguration; import org.springframework.boot.autoconfigure.AutoConfigureAfter; import org.springframework.boot.autoconfigure.EnableAutoConfiguration; @@ -39,12 +43,14 @@ import org.springframework.boot.context.properties.EnableConfigurationProperties import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.core.annotation.AnnotationUtils; +import org.springframework.core.annotation.Order; /** * {@link EnableAutoConfiguration Auto-configuration} for Jersey server instrumentation. * * @author Michael Weirauch * @author Michael Simons + * @author Andy Wilkinson * @since 2.1.0 */ @Configuration @@ -53,9 +59,15 @@ import org.springframework.core.annotation.AnnotationUtils; @ConditionalOnWebApplication(type = ConditionalOnWebApplication.Type.SERVLET) @ConditionalOnClass({ ResourceConfig.class, MetricsApplicationEventListener.class }) @ConditionalOnBean({ MeterRegistry.class, ResourceConfig.class }) -@EnableConfigurationProperties(JerseyServerMetricsProperties.class) +@EnableConfigurationProperties(MetricsProperties.class) public class JerseyServerMetricsAutoConfiguration { + private final MetricsProperties properties; + + public JerseyServerMetricsAutoConfiguration(MetricsProperties properties) { + this.properties = properties; + } + @Bean @ConditionalOnMissingBean(JerseyTagsProvider.class) public DefaultJerseyTagsProvider jerseyTagsProvider() { @@ -64,18 +76,36 @@ public class JerseyServerMetricsAutoConfiguration { @Bean public ResourceConfigCustomizer jerseyServerMetricsResourceConfigCustomizer( - MeterRegistry meterRegistry, JerseyServerMetricsProperties properties, - JerseyTagsProvider tagsProvider) { - return (config) -> config.register(new MetricsApplicationEventListener( - meterRegistry, tagsProvider, properties.getRequestsMetricName(), - properties.isAutoTimeRequests(), new AnnotationFinder() { - @Override - public A findAnnotation( - AnnotatedElement annotatedElement, Class annotationType) { - return AnnotationUtils.findAnnotation(annotatedElement, - annotationType); - } - })); + MeterRegistry meterRegistry, JerseyTagsProvider tagsProvider) { + Server server = this.properties.getWeb().getServer(); + return (config) -> { + config.register(new MetricsApplicationEventListener(meterRegistry, + tagsProvider, server.getRequestsMetricName(), + server.isAutoTimeRequests(), new AnnotationUtilsAnnotationFinder())); + }; + } + + @Bean + @Order(0) + public MeterFilter jerseyMetricsUriTagFilter() { + String metricName = this.properties.getWeb().getServer().getRequestsMetricName(); + MeterFilter filter = new OnlyOnceLoggingDenyMeterFilter(() -> String + .format("Reached the maximum number of URI tags for '%s'.", metricName)); + return MeterFilter.maximumAllowableTags(metricName, "uri", + this.properties.getWeb().getServer().getMaxUriTags(), filter); + } + + /** + * An {@link AnnotationFinder} that uses {@link AnnotationUtils}. + */ + private static class AnnotationUtilsAnnotationFinder implements AnnotationFinder { + + @Override + public A findAnnotation(AnnotatedElement annotatedElement, + Class annotationType) { + return AnnotationUtils.findAnnotation(annotatedElement, annotationType); + } + } } diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/package-info.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/package-info.java similarity index 90% rename from spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/package-info.java rename to spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/package-info.java index 093d228878..6a57de0f6a 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/package-info.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/package-info.java @@ -15,6 +15,6 @@ */ /** - * Auto-configuration for Jersey server actuator metrics. + * Auto-configuration for Jersey actuator metrics. */ -package org.springframework.boot.actuate.autoconfigure.metrics.jersey2.server; +package org.springframework.boot.actuate.autoconfigure.metrics.jersey; diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsProperties.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsProperties.java deleted file mode 100644 index 8fddb1e8a4..0000000000 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsProperties.java +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Copyright 2012-2018 the original author or authors. - * - * Licensed 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.springframework.boot.actuate.autoconfigure.metrics.jersey2.server; - -import org.springframework.boot.context.properties.ConfigurationProperties; - -/** - * Configuration for Jersey server instrumentation. - * - * @author Michael Weirauch - * @since 2.1.0 - */ -@ConfigurationProperties(prefix = "management.metrics.jersey2.server") -public class JerseyServerMetricsProperties { - - private String requestsMetricName = "http.server.requests"; - - private boolean autoTimeRequests = true; - - public String getRequestsMetricName() { - return this.requestsMetricName; - } - - public void setRequestsMetricName(String requestsMetricName) { - this.requestsMetricName = requestsMetricName; - } - - public boolean isAutoTimeRequests() { - return this.autoTimeRequests; - } - - public void setAutoTimeRequests(boolean autoTimeRequests) { - this.autoTimeRequests = autoTimeRequests; - } - -} diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/resources/META-INF/spring.factories b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/resources/META-INF/spring.factories index 122c561674..29af9cef1b 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/resources/META-INF/spring.factories +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/resources/META-INF/spring.factories @@ -61,7 +61,7 @@ org.springframework.boot.actuate.autoconfigure.metrics.export.simple.SimpleMetri org.springframework.boot.actuate.autoconfigure.metrics.export.statsd.StatsdMetricsExportAutoConfiguration,\ org.springframework.boot.actuate.autoconfigure.metrics.export.wavefront.WavefrontMetricsExportAutoConfiguration,\ org.springframework.boot.actuate.autoconfigure.metrics.jdbc.DataSourcePoolMetricsAutoConfiguration,\ -org.springframework.boot.actuate.autoconfigure.metrics.jersey2.server.JerseyServerMetricsAutoConfiguration,\ +org.springframework.boot.actuate.autoconfigure.metrics.jersey.JerseyServerMetricsAutoConfiguration,\ org.springframework.boot.actuate.autoconfigure.metrics.orm.jpa.HibernateMetricsAutoConfiguration,\ org.springframework.boot.actuate.autoconfigure.metrics.web.client.HttpClientMetricsAutoConfiguration,\ org.springframework.boot.actuate.autoconfigure.metrics.web.reactive.WebFluxMetricsAutoConfiguration,\ diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsAutoConfigurationTests.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfigurationTests.java similarity index 99% rename from spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsAutoConfigurationTests.java rename to spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfigurationTests.java index 6d27eae953..8fdc463200 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey2/server/JerseyServerMetricsAutoConfigurationTests.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfigurationTests.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package org.springframework.boot.actuate.autoconfigure.metrics.jersey2.server; +package org.springframework.boot.actuate.autoconfigure.metrics.jersey; import java.net.URI; @@ -97,7 +97,6 @@ public class JerseyServerMetricsAutoConfigurationTests { public void httpRequestsAreTimed() { this.webContextRunner.run((context) -> { doRequest(context); - MeterRegistry registry = context.getBean(MeterRegistry.class); Timer timer = registry.get("http.server.requests").tag("uri", "/users/{id}") .timer(); diff --git a/spring-boot-project/spring-boot-docs/src/main/asciidoc/production-ready-features.adoc b/spring-boot-project/spring-boot-docs/src/main/asciidoc/production-ready-features.adoc index 40d7d78158..b05de13fcc 100644 --- a/spring-boot-project/spring-boot-docs/src/main/asciidoc/production-ready-features.adoc +++ b/spring-boot-project/spring-boot-docs/src/main/asciidoc/production-ready-features.adoc @@ -1835,9 +1835,9 @@ To customize the tags, provide a `@Bean` that implements `WebFluxTagsProvider`. [[production-ready-metrics-jersey-server]] ==== Jersey Server Metrics Auto-configuration enables the instrumentation of requests handled by the Jersey JAX-RS -implementation. When `management.metrics.jersey2.server.auto-time-requests` is `true`, -this instrumentation occurs for all requests. Alternatively, when set to `false`, you -can enable instrumentation by adding `@Timed` to a request-handling method: +implementation. When `management.metrics.web.server.auto-time-requests` is `true`, this +instrumentation occurs for all requests. Alternatively, when set to `false`, you can +enable instrumentation by adding `@Timed` to a request-handling method: [source,java,indent=0] ---- @@ -1858,7 +1858,7 @@ the class, but can be used to further customize the timer for this particular en timers require a separate metric name, and can be stacked with a short task timer. By default, metrics are generated with the name, `http.server.requests`. The name can be -customized by setting the `management.metrics.jersey2.server.requests-metric-name` property. +customized by setting the `management.metrics.web.server.requests-metric-name` property. By default, Jersey server metrics are tagged with the following information: