From 02715a3b141e20ebb4d0ec997e2df9ed820a31b2 Mon Sep 17 00:00:00 2001 From: Tadaya Tsuyukubo Date: Wed, 17 Apr 2019 17:46:06 -0700 Subject: [PATCH] Add properties for default config of auto-timed metrics When `management.metrics.web.server.auto-time-requests` is enabled (default=true), spring-boot collects metrics on controller methods even when they are not annotated with `@Timed`. When this happens, created metrics are based on the default configuration values of `@Timed`. Currently, there is no way to specify the default configuration to those auto-timed controller metrics. This commit adds default configurations to auto-time requests on both client and server sides. These properties are introduced: - "management.metrics.web.[server|client].request.auto-time.enabled" - "management.metrics.web.[server|client].request.auto-time.default-percentiles" - "management.metrics.web.[server|client].request.auto-time.default-histogram" Also, "requests-metric-name" property is updated: old: "management.metrics.web.[server|client].requests-metric-name" new: "management.metrics.web.[server|client].request.metric-name" This property is removed: - `management.metrics.web.server.auto-time-requests` --- .../metrics/MetricsProperties.java | 166 +++++++++++++++--- .../JerseyServerMetricsAutoConfiguration.java | 8 +- .../HttpClientMetricsAutoConfiguration.java | 2 +- .../RestTemplateMetricsConfiguration.java | 10 +- .../client/WebClientMetricsConfiguration.java | 2 +- .../WebFluxMetricsAutoConfiguration.java | 11 +- .../WebMvcMetricsAutoConfiguration.java | 9 +- .../WebFluxMetricsAutoConfigurationTests.java | 2 +- .../WebMvcMetricsAutoConfigurationTests.java | 24 +++ .../MetricsClientHttpRequestInterceptor.java | 48 ++++- .../client/MetricsRestTemplateCustomizer.java | 22 +++ .../MetricsWebClientFilterFunction.java | 45 ++++- .../web/reactive/server/MetricsWebFilter.java | 73 ++++++-- .../web/servlet/WebMvcMetricsFilter.java | 36 +++- .../MetricsRestTemplateCustomizerTests.java | 3 +- .../server/MetricsWebFilterTests.java | 3 +- .../WebMvcMetricsFilterAutoTimedTests.java | 16 +- .../web/servlet/WebMvcMetricsFilterTests.java | 2 +- .../WebMvcMetricsIntegrationTests.java | 2 +- .../asciidoc/production-ready-features.adoc | 4 +- 20 files changed, 416 insertions(+), 72 deletions(-) diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/MetricsProperties.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/MetricsProperties.java index f925a1499317..9ee07b42cd93 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/MetricsProperties.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/MetricsProperties.java @@ -16,16 +16,20 @@ package org.springframework.boot.actuate.autoconfigure.metrics; +import java.util.ArrayList; import java.util.LinkedHashMap; +import java.util.List; import java.util.Map; import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.boot.context.properties.DeprecatedConfigurationProperty; /** * {@link ConfigurationProperties} for configuring Micrometer-based metrics. * * @author Jon Schneider * @author Alexander Abramov + * @author Tadaya Tsuyukubo * @since 2.0.0 */ @ConfigurationProperties("management.metrics") @@ -93,10 +97,79 @@ public Server getServer() { public static class Client { + private final ClientRequest request = new ClientRequest(); + + /** + * Maximum number of unique URI tag values allowed. After the max number of + * tag values is reached, metrics with additional tag values are denied by + * filter. + */ + private int maxUriTags = 100; + /** - * Name of the metric for sent requests. + * Get name of the metric for received requests. + * @return request metric name + * @deprecated since 2.2.0 in favor of {@link ClientRequest#getMetricName()} */ - private String requestsMetricName = "http.client.requests"; + @DeprecatedConfigurationProperty( + replacement = "management.metrics.web.client.request.metric-name") + public String getRequestsMetricName() { + return this.request.getMetricName(); + } + + /** + * Set name of the metric for received requests. + * @param requestsMetricName request metric name + * @deprecated since 2.2.0 in favor of + * {@link ClientRequest#setMetricName(String)} + */ + public void setRequestsMetricName(String requestsMetricName) { + this.request.setMetricName(requestsMetricName); + } + + public ClientRequest getRequest() { + return this.request; + } + + public int getMaxUriTags() { + return this.maxUriTags; + } + + public void setMaxUriTags(int maxUriTags) { + this.maxUriTags = maxUriTags; + } + + public static class ClientRequest { + + /** + * Name of the metric for sent requests. + */ + private String metricName = "http.client.requests"; + + /** + * Automatically time requests. + */ + private final AutoTime autoTime = new AutoTime(); + + public AutoTime getAutoTime() { + return this.autoTime; + } + + public String getMetricName() { + return this.metricName; + } + + public void setMetricName(String metricName) { + this.metricName = metricName; + } + + } + + } + + public static class Server { + + private final ServerRequest request = new ServerRequest(); /** * Maximum number of unique URI tag values allowed. After the max number of @@ -105,12 +178,29 @@ public static class Client { */ private int maxUriTags = 100; + /** + * Get name of the metric for received requests. + * @return request metric name + * @deprecated since 2.2.0 in favor of {@link ServerRequest#getMetricName()} + */ + @DeprecatedConfigurationProperty( + replacement = "management.metrics.web.server.request.metric-name") public String getRequestsMetricName() { - return this.requestsMetricName; + return this.request.getMetricName(); } + /** + * Set name of the metric for received requests. + * @param requestsMetricName request metric name + * @deprecated since 2.2.0 in favor of + * {@link ServerRequest#setMetricName(String)} + */ public void setRequestsMetricName(String requestsMetricName) { - this.requestsMetricName = requestsMetricName; + this.request.setMetricName(requestsMetricName); + } + + public ServerRequest getRequest() { + return this.request; } public int getMaxUriTags() { @@ -121,9 +211,35 @@ public void setMaxUriTags(int maxUriTags) { this.maxUriTags = maxUriTags; } + public static class ServerRequest { + + /** + * Name of the metric for received requests. + */ + private String metricName = "http.server.requests"; + + /** + * Automatically time requests. + */ + private final AutoTime autoTime = new AutoTime(); + + public AutoTime getAutoTime() { + return this.autoTime; + } + + public String getMetricName() { + return this.metricName; + } + + public void setMetricName(String metricName) { + this.metricName = metricName; + } + + } + } - public static class Server { + public static class AutoTime { /** * Whether requests handled by Spring MVC, WebFlux or Jersey should be @@ -131,42 +247,44 @@ public static class Server { * on account of request mapping timings, disable this and use 'Timed' on a * per request mapping basis as needed. */ - private boolean autoTimeRequests = true; + private boolean enabled = true; /** - * Name of the metric for received requests. + * Default percentiles when @Timed annotation is not presented on the + * corresponding request handler. Any @Timed annotation presented will have + * precedence. */ - private String requestsMetricName = "http.server.requests"; + private List defaultPercentiles = new ArrayList<>(); /** - * Maximum number of unique URI tag values allowed. After the max number of - * tag values is reached, metrics with additional tag values are denied by - * filter. + * Default histogram when @Timed annotation is not presented on the + * corresponding request handler. Any @Timed annotation presented will have + * precedence. */ - private int maxUriTags = 100; + private boolean defaultHistogram; - public boolean isAutoTimeRequests() { - return this.autoTimeRequests; + public boolean isEnabled() { + return this.enabled; } - public void setAutoTimeRequests(boolean autoTimeRequests) { - this.autoTimeRequests = autoTimeRequests; + public void setEnabled(boolean enabled) { + this.enabled = enabled; } - public String getRequestsMetricName() { - return this.requestsMetricName; + public List getDefaultPercentiles() { + return this.defaultPercentiles; } - public void setRequestsMetricName(String requestsMetricName) { - this.requestsMetricName = requestsMetricName; + public void setDefaultPercentiles(List defaultPercentiles) { + this.defaultPercentiles = defaultPercentiles; } - public int getMaxUriTags() { - return this.maxUriTags; + public boolean isDefaultHistogram() { + return this.defaultHistogram; } - public void setMaxUriTags(int maxUriTags) { - this.maxUriTags = maxUriTags; + public void setDefaultHistogram(boolean defaultHistogram) { + this.defaultHistogram = defaultHistogram; } } diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfiguration.java index ec10ae311f22..d5d6d923ec4a 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/jersey/JerseyServerMetricsAutoConfiguration.java @@ -79,14 +79,16 @@ public ResourceConfigCustomizer jerseyServerMetricsResourceConfigCustomizer( MeterRegistry meterRegistry, JerseyTagsProvider tagsProvider) { Server server = this.properties.getWeb().getServer(); return (config) -> config.register(new MetricsApplicationEventListener( - meterRegistry, tagsProvider, server.getRequestsMetricName(), - server.isAutoTimeRequests(), new AnnotationUtilsAnnotationFinder())); + meterRegistry, tagsProvider, server.getRequest().getMetricName(), + server.getRequest().getAutoTime().isEnabled(), + new AnnotationUtilsAnnotationFinder())); } @Bean @Order(0) public MeterFilter jerseyMetricsUriTagFilter() { - String metricName = this.properties.getWeb().getServer().getRequestsMetricName(); + String metricName = this.properties.getWeb().getServer().getRequest() + .getMetricName(); MeterFilter filter = new OnlyOnceLoggingDenyMeterFilter(() -> String .format("Reached the maximum number of URI tags for '%s'.", metricName)); return MeterFilter.maximumAllowableTags(metricName, "uri", diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/HttpClientMetricsAutoConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/HttpClientMetricsAutoConfiguration.java index def5e7174a10..6fdb0a8ad0b7 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/HttpClientMetricsAutoConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/HttpClientMetricsAutoConfiguration.java @@ -53,7 +53,7 @@ public class HttpClientMetricsAutoConfiguration { @Bean @Order(0) public MeterFilter metricsHttpClientUriTagFilter(MetricsProperties properties) { - String metricName = properties.getWeb().getClient().getRequestsMetricName(); + String metricName = properties.getWeb().getClient().getRequest().getMetricName(); MeterFilter denyFilter = new OnlyOnceLoggingDenyMeterFilter(() -> String .format("Reached the maximum number of URI tags for '%s'. Are you using " + "'uriVariables'?", metricName)); diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/RestTemplateMetricsConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/RestTemplateMetricsConfiguration.java index 6ec64b51a39f..7326b90743d0 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/RestTemplateMetricsConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/RestTemplateMetricsConfiguration.java @@ -19,6 +19,8 @@ import io.micrometer.core.instrument.MeterRegistry; import org.springframework.boot.actuate.autoconfigure.metrics.MetricsProperties; +import org.springframework.boot.actuate.autoconfigure.metrics.MetricsProperties.Web.AutoTime; +import org.springframework.boot.actuate.autoconfigure.metrics.MetricsProperties.Web.Client; import org.springframework.boot.actuate.metrics.web.client.DefaultRestTemplateExchangeTagsProvider; import org.springframework.boot.actuate.metrics.web.client.MetricsRestTemplateCustomizer; import org.springframework.boot.actuate.metrics.web.client.RestTemplateExchangeTagsProvider; @@ -53,9 +55,13 @@ public MetricsRestTemplateCustomizer metricsRestTemplateCustomizer( MeterRegistry meterRegistry, RestTemplateExchangeTagsProvider restTemplateExchangeTagsProvider, MetricsProperties properties) { + + Client client = properties.getWeb().getClient(); + AutoTime autoTime = client.getRequest().getAutoTime(); return new MetricsRestTemplateCustomizer(meterRegistry, - restTemplateExchangeTagsProvider, - properties.getWeb().getClient().getRequestsMetricName()); + restTemplateExchangeTagsProvider, client.getRequest().getMetricName(), + autoTime.isEnabled(), autoTime.getDefaultPercentiles(), + autoTime.isDefaultHistogram()); } } diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/WebClientMetricsConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/WebClientMetricsConfiguration.java index dbbf4e062830..5a88d7216654 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/WebClientMetricsConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/client/WebClientMetricsConfiguration.java @@ -49,7 +49,7 @@ public MetricsWebClientCustomizer metricsWebClientCustomizer( MeterRegistry meterRegistry, WebClientExchangeTagsProvider tagsProvider, MetricsProperties properties) { return new MetricsWebClientCustomizer(meterRegistry, tagsProvider, - properties.getWeb().getClient().getRequestsMetricName()); + properties.getWeb().getClient().getRequest().getMetricName()); } } diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfiguration.java index 87280c544849..1d03e8712272 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfiguration.java @@ -21,6 +21,8 @@ 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.AutoTime; +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.actuate.metrics.web.reactive.server.DefaultWebFluxTagsProvider; @@ -65,15 +67,18 @@ public DefaultWebFluxTagsProvider webfluxTagConfigurer() { @Bean public MetricsWebFilter webfluxMetrics(MeterRegistry registry, WebFluxTagsProvider tagConfigurer) { + Server serverProperties = this.properties.getWeb().getServer(); + AutoTime autotime = serverProperties.getRequest().getAutoTime(); return new MetricsWebFilter(registry, tagConfigurer, - this.properties.getWeb().getServer().getRequestsMetricName(), - this.properties.getWeb().getServer().isAutoTimeRequests()); + serverProperties.getRequest().getMetricName(), autotime.isEnabled(), + autotime.getDefaultPercentiles(), autotime.isDefaultHistogram()); } @Bean @Order(0) public MeterFilter metricsHttpServerUriTagFilter() { - String metricName = this.properties.getWeb().getServer().getRequestsMetricName(); + String metricName = this.properties.getWeb().getServer().getRequest() + .getMetricName(); MeterFilter filter = new OnlyOnceLoggingDenyMeterFilter(() -> String .format("Reached the maximum number of URI tags for '%s'.", metricName)); return MeterFilter.maximumAllowableTags(metricName, "uri", diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfiguration.java index ffa95accfe36..4463fac6155d 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfiguration.java @@ -23,6 +23,7 @@ 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.AutoTime; 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; @@ -79,9 +80,10 @@ public DefaultWebMvcTagsProvider webMvcTagsProvider() { public FilterRegistrationBean webMvcMetricsFilter( MeterRegistry registry, WebMvcTagsProvider tagsProvider) { Server serverProperties = this.properties.getWeb().getServer(); + AutoTime autotime = serverProperties.getRequest().getAutoTime(); WebMvcMetricsFilter filter = new WebMvcMetricsFilter(registry, tagsProvider, - serverProperties.getRequestsMetricName(), - serverProperties.isAutoTimeRequests()); + serverProperties.getRequest().getMetricName(), autotime.isEnabled(), + autotime.getDefaultPercentiles(), autotime.isDefaultHistogram()); FilterRegistrationBean registration = new FilterRegistrationBean<>( filter); registration.setOrder(Ordered.HIGHEST_PRECEDENCE + 1); @@ -92,7 +94,8 @@ public FilterRegistrationBean webMvcMetricsFilter( @Bean @Order(0) public MeterFilter metricsHttpServerUriTagFilter() { - String metricName = this.properties.getWeb().getServer().getRequestsMetricName(); + String metricName = this.properties.getWeb().getServer().getRequest() + .getMetricName(); MeterFilter filter = new OnlyOnceLoggingDenyMeterFilter(() -> String .format("Reached the maximum number of URI tags for '%s'.", metricName)); return MeterFilter.maximumAllowableTags(metricName, "uri", diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfigurationTests.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfigurationTests.java index e61bcd04f99a..6b15f1a95b7d 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfigurationTests.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/reactive/WebFluxMetricsAutoConfigurationTests.java @@ -102,7 +102,7 @@ public void metricsAreNotRecordedIfAutoTimeRequestsIsDisabled() { .withConfiguration(AutoConfigurations.of(WebFluxAutoConfiguration.class)) .withUserConfiguration(TestController.class) .withPropertyValues( - "management.metrics.web.server.auto-time-requests=false") + "management.metrics.web.server.request.auto-time.enabled=false") .run((context) -> { MeterRegistry registry = getInitializedMeterRegistry(context); assertThat(registry.find("http.server.requests").meter()).isNull(); diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfigurationTests.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfigurationTests.java index bb5eb901d445..898c499da739 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfigurationTests.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/metrics/web/servlet/WebMvcMetricsAutoConfigurationTests.java @@ -26,6 +26,8 @@ import io.micrometer.core.instrument.MeterRegistry; import io.micrometer.core.instrument.Tag; +import io.micrometer.core.instrument.Timer; +import io.micrometer.core.instrument.distribution.HistogramSnapshot; import org.junit.Rule; import org.junit.Test; @@ -58,6 +60,7 @@ * * @author Andy Wilkinson * @author Dmytro Nosan + * @author Tadaya Tsuyukubo */ public class WebMvcMetricsAutoConfigurationTests { @@ -137,6 +140,27 @@ public void shouldNotDenyNorLogIfMaxUrisIsNotReached() { }); } + @Test + public void autoTimeRequestsDefaultValues() { + this.contextRunner.withUserConfiguration(TestController.class) + .withConfiguration(AutoConfigurations.of(MetricsAutoConfiguration.class, + WebMvcAutoConfiguration.class)) + .withPropertyValues( + "management.metrics.web.server.request.auto-time.enabled=true", + "management.metrics.web.server.request.auto-time.default-percentiles=0.5,0.7", + "management.metrics.web.server.request.auto-time.default-histogram=true") + .run((context) -> { + MeterRegistry registry = getInitializedMeterRegistry(context); + Timer timer = registry.get("http.server.requests").timer(); + HistogramSnapshot snapshot = timer.takeSnapshot(); + assertThat(snapshot.percentileValues()).hasSize(2); + assertThat(snapshot.percentileValues()[0].percentile()) + .isEqualTo(0.5); + assertThat(snapshot.percentileValues()[1].percentile()) + .isEqualTo(0.7); + }); + } + @Test @SuppressWarnings("rawtypes") public void longTaskTimingInterceptorIsRegistered() { diff --git a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsClientHttpRequestInterceptor.java b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsClientHttpRequestInterceptor.java index 0d2d611f4b0d..63c2a4d5535e 100644 --- a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsClientHttpRequestInterceptor.java +++ b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsClientHttpRequestInterceptor.java @@ -18,6 +18,7 @@ import java.io.IOException; import java.net.URI; +import java.util.List; import java.util.Map; import java.util.concurrent.TimeUnit; @@ -50,11 +51,49 @@ class MetricsClientHttpRequestInterceptor implements ClientHttpRequestIntercepto private final String metricName; + private final boolean autoTimeRequests; + + private final double[] percentiles; + + private final boolean histogram; + + /** + * Create a new {@code MetricsClientHttpRequestInterceptor}. + * @param meterRegistry the registry to which metrics are recorded + * @param tagProvider provider for metrics tags + * @param metricName name of the metric to record + * @deprecated since 2.2.0 in favor of + * {@link #MetricsClientHttpRequestInterceptor(MeterRegistry, RestTemplateExchangeTagsProvider, String, boolean, List, boolean)} + */ MetricsClientHttpRequestInterceptor(MeterRegistry meterRegistry, RestTemplateExchangeTagsProvider tagProvider, String metricName) { + this(meterRegistry, tagProvider, metricName, true, null, false); + } + + /** + * Create a new {@code MetricsClientHttpRequestInterceptor}. + * @param meterRegistry the registry to which metrics are recorded + * @param tagProvider provider for metrics tags + * @param metricName name of the metric to record + * @param autoTimeRequests if requests should be automatically timed + * @param percentileList percentiles for auto time requests + * @param histogram histogram or not for auto time requests + * @since 2.2.0 + */ + MetricsClientHttpRequestInterceptor(MeterRegistry meterRegistry, + RestTemplateExchangeTagsProvider tagProvider, String metricName, + boolean autoTimeRequests, List percentileList, boolean histogram) { + + double[] percentiles = (percentileList != null) + ? percentileList.stream().mapToDouble(Double::doubleValue).toArray() + : null; + this.tagProvider = tagProvider; this.meterRegistry = meterRegistry; this.metricName = metricName; + this.autoTimeRequests = autoTimeRequests; + this.percentiles = percentiles; + this.histogram = histogram; } @Override @@ -67,8 +106,10 @@ public ClientHttpResponse intercept(HttpRequest request, byte[] body, return response; } finally { - getTimeBuilder(request, response).register(this.meterRegistry) - .record(System.nanoTime() - startTime, TimeUnit.NANOSECONDS); + if (this.autoTimeRequests) { + getTimeBuilder(request, response).register(this.meterRegistry) + .record(System.nanoTime() - startTime, TimeUnit.NANOSECONDS); + } urlTemplate.remove(); } } @@ -93,7 +134,8 @@ public URI expand(String url, Object... arguments) { private Timer.Builder getTimeBuilder(HttpRequest request, ClientHttpResponse response) { - return Timer.builder(this.metricName) + return Timer.builder(this.metricName).publishPercentiles(this.percentiles) + .publishPercentileHistogram(this.histogram) .tags(this.tagProvider.getTags(urlTemplate.get(), request, response)) .description("Timer of RestTemplate operation"); } diff --git a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizer.java b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizer.java index 0755feadaa06..ac3892db2f69 100644 --- a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizer.java +++ b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizer.java @@ -45,6 +45,8 @@ public class MetricsRestTemplateCustomizer implements RestTemplateCustomizer { * @param meterRegistry the meter registry * @param tagProvider the tag provider * @param metricName the name of the recorded metric + * @deprecated since 2.2.0 in favor of + * {@link #MetricsRestTemplateCustomizer(MeterRegistry, RestTemplateExchangeTagsProvider, String, boolean, List, boolean)} */ public MetricsRestTemplateCustomizer(MeterRegistry meterRegistry, RestTemplateExchangeTagsProvider tagProvider, String metricName) { @@ -52,6 +54,26 @@ public MetricsRestTemplateCustomizer(MeterRegistry meterRegistry, tagProvider, metricName); } + /** + * Creates a new {@code MetricsRestTemplateInterceptor}. When {@code autoTimeRequests} + * is set to {@code true}, the interceptor records metrics using the given + * {@code meterRegistry} with tags provided by the given {@code tagProvider} and with + * {@code percentileList} and {@code histogram} configurations. + * @param meterRegistry the meter registry + * @param tagProvider the tag provider + * @param metricName the name of the recorded metric + * @param autoTimeRequests if requests should be automatically timed + * @param percentileList percentiles for auto time requests + * @param histogram histogram or not for auto time requests + * @since 2.2.0 + */ + public MetricsRestTemplateCustomizer(MeterRegistry meterRegistry, + RestTemplateExchangeTagsProvider tagProvider, String metricName, + boolean autoTimeRequests, List percentileList, boolean histogram) { + this.interceptor = new MetricsClientHttpRequestInterceptor(meterRegistry, + tagProvider, metricName, autoTimeRequests, percentileList, histogram); + } + @Override public void customize(RestTemplate restTemplate) { UriTemplateHandler templateHandler = restTemplate.getUriTemplateHandler(); diff --git a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/client/MetricsWebClientFilterFunction.java b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/client/MetricsWebClientFilterFunction.java index 63fd9c00c730..0fc99967f82a 100644 --- a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/client/MetricsWebClientFilterFunction.java +++ b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/client/MetricsWebClientFilterFunction.java @@ -16,6 +16,7 @@ package org.springframework.boot.actuate.metrics.web.reactive.client; +import java.util.List; import java.util.concurrent.TimeUnit; import io.micrometer.core.instrument.MeterRegistry; @@ -33,6 +34,7 @@ * record metrics. * * @author Brian Clozel + * @author Tadaya Tsuyukubo * @since 2.1.0 */ public class MetricsWebClientFilterFunction implements ExchangeFilterFunction { @@ -46,24 +48,63 @@ public class MetricsWebClientFilterFunction implements ExchangeFilterFunction { private final String metricName; + private final boolean autoTimeRequests; + + private final double[] percentiles; + + private final boolean histogram; + + /** + * Create a new {@code MetricsWebClientFilterFunction}. + * @param meterRegistry the registry to which metrics are recorded + * @param tagProvider provider for metrics tags + * @param metricName name of the metric to record + * @deprecated since 2.2.0 in favor of + * {@link #MetricsWebClientFilterFunction(MeterRegistry, WebClientExchangeTagsProvider, String, boolean, List, boolean)} + */ public MetricsWebClientFilterFunction(MeterRegistry meterRegistry, WebClientExchangeTagsProvider tagProvider, String metricName) { + this(meterRegistry, tagProvider, metricName, true, null, false); + } + + /** + * Create a new {@code MetricsWebClientFilterFunction}. + * @param meterRegistry the registry to which metrics are recorded + * @param tagProvider provider for metrics tags + * @param metricName name of the metric to record + * @param autoTimeRequests if requests should be automatically timed + * @param percentileList percentiles for auto time requests + * @param histogram histogram or not for auto time requests + * @since 2.2.0 + */ + public MetricsWebClientFilterFunction(MeterRegistry meterRegistry, + WebClientExchangeTagsProvider tagProvider, String metricName, + boolean autoTimeRequests, List percentileList, boolean histogram) { + + double[] percentiles = (percentileList != null) + ? percentileList.stream().mapToDouble(Double::doubleValue).toArray() + : null; + this.meterRegistry = meterRegistry; this.tagProvider = tagProvider; this.metricName = metricName; + this.autoTimeRequests = autoTimeRequests; + this.percentiles = percentiles; + this.histogram = histogram; } @Override public Mono filter(ClientRequest clientRequest, ExchangeFunction exchangeFunction) { return exchangeFunction.exchange(clientRequest).doOnEach((signal) -> { - if (!signal.isOnComplete()) { + if (!signal.isOnComplete() && this.autoTimeRequests) { Long startTime = signal.getContext().get(METRICS_WEBCLIENT_START_TIME); ClientResponse clientResponse = signal.get(); Throwable throwable = signal.getThrowable(); Iterable tags = this.tagProvider.tags(clientRequest, clientResponse, throwable); - Timer.builder(this.metricName).tags(tags) + Timer.builder(this.metricName).publishPercentiles(this.percentiles) + .publishPercentileHistogram(this.histogram).tags(tags) .description("Timer of WebClient operation") .register(this.meterRegistry) .record(System.nanoTime() - startTime, TimeUnit.NANOSECONDS); diff --git a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilter.java b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilter.java index 64a698a801cb..6659a93025fc 100644 --- a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilter.java +++ b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilter.java @@ -16,10 +16,12 @@ package org.springframework.boot.actuate.metrics.web.reactive.server; +import java.util.List; import java.util.concurrent.TimeUnit; import io.micrometer.core.instrument.MeterRegistry; import io.micrometer.core.instrument.Tag; +import io.micrometer.core.instrument.Timer; import org.reactivestreams.Publisher; import reactor.core.publisher.Mono; @@ -48,12 +50,49 @@ public class MetricsWebFilter implements WebFilter { private final boolean autoTimeRequests; + private final double[] percentiles; + + private final boolean histogram; + + /** + * Create a new {@code MetricsWebFilter}. + * @param registry the registry to which metrics are recorded + * @param tagsProvider provider for metrics tags + * @param metricName name of the metric to record + * @param autoTimeRequests if requests should be automatically timed + * @deprecated since 2.2.0 in favor of + * {@link #MetricsWebFilter(MeterRegistry, WebFluxTagsProvider, String, boolean, List, boolean)} + */ + @Deprecated public MetricsWebFilter(MeterRegistry registry, WebFluxTagsProvider tagsProvider, String metricName, boolean autoTimeRequests) { + this(registry, tagsProvider, metricName, autoTimeRequests, null, false); + } + + /** + * Create a new {@code MetricsWebFilter}. + * @param registry the registry to which metrics are recorded + * @param tagsProvider provider for metrics tags + * @param metricName name of the metric to record + * @param autoTimeRequests if requests should be automatically timed + * @param percentileList percentiles for auto time requests + * @param histogram histogram or not for auto time requests + * @since 2.2.0 + */ + public MetricsWebFilter(MeterRegistry registry, WebFluxTagsProvider tagsProvider, + String metricName, boolean autoTimeRequests, List percentileList, + boolean histogram) { + + double[] percentiles = (percentileList != null) + ? percentileList.stream().mapToDouble(Double::doubleValue).toArray() + : null; + this.registry = registry; this.tagsProvider = tagsProvider; this.metricName = metricName; this.autoTimeRequests = autoTimeRequests; + this.percentiles = percentiles; + this.histogram = histogram; } @Override @@ -67,29 +106,25 @@ public Mono filter(ServerWebExchange exchange, WebFilterChain chain) { private Publisher filter(ServerWebExchange exchange, Mono call) { long start = System.nanoTime(); ServerHttpResponse response = exchange.getResponse(); - return call.doOnSuccess((done) -> success(exchange, start)).doOnError((cause) -> { - if (response.isCommitted()) { - error(exchange, start, cause); - } - else { - response.beforeCommit(() -> { - error(exchange, start, cause); - return Mono.empty(); + return call.doOnSuccess((done) -> record(exchange, start, null)) + .doOnError((cause) -> { + if (response.isCommitted()) { + record(exchange, start, cause); + } + else { + response.beforeCommit(() -> { + record(exchange, start, cause); + return Mono.empty(); + }); + } }); - } - }); - } - - private void success(ServerWebExchange exchange, long start) { - Iterable tags = this.tagsProvider.httpRequestTags(exchange, null); - this.registry.timer(this.metricName, tags).record(System.nanoTime() - start, - TimeUnit.NANOSECONDS); } - private void error(ServerWebExchange exchange, long start, Throwable cause) { + private void record(ServerWebExchange exchange, long start, Throwable cause) { Iterable tags = this.tagsProvider.httpRequestTags(exchange, cause); - this.registry.timer(this.metricName, tags).record(System.nanoTime() - start, - TimeUnit.NANOSECONDS); + Timer.builder(this.metricName).tags(tags).publishPercentiles(this.percentiles) + .publishPercentileHistogram(this.histogram).register(this.registry) + .record(System.nanoTime() - start, TimeUnit.NANOSECONDS); } } diff --git a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilter.java b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilter.java index 39bb72e35286..1624ad0ac0fd 100644 --- a/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilter.java +++ b/spring-boot-project/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilter.java @@ -19,6 +19,7 @@ import java.io.IOException; import java.lang.reflect.AnnotatedElement; import java.util.Collections; +import java.util.List; import java.util.Set; import java.util.function.Supplier; @@ -60,6 +61,10 @@ public class WebMvcMetricsFilter extends OncePerRequestFilter { private final boolean autoTimeRequests; + private final double[] autoTimeRequestsPercentiles; + + private final boolean autoTimeRequestsHistogram; + /** * Create a new {@link WebMvcMetricsFilter} instance. * @param registry the meter registry @@ -67,13 +72,40 @@ public class WebMvcMetricsFilter extends OncePerRequestFilter { * @param metricName the metric name * @param autoTimeRequests if requests should be automatically timed * @since 2.0.7 + * @deprecated since 2.1.4 in favor of + * {@link #WebMvcMetricsFilter(MeterRegistry, WebMvcTagsProvider, String, boolean, List, boolean)} */ + @Deprecated public WebMvcMetricsFilter(MeterRegistry registry, WebMvcTagsProvider tagsProvider, String metricName, boolean autoTimeRequests) { + this(registry, tagsProvider, metricName, autoTimeRequests, null, false); + } + + /** + * Create a new {@link WebMvcMetricsFilter} instance. + * @param registry the meter registry + * @param tagsProvider the tags provider + * @param metricName the metric name + * @param autoTimeRequests if requests should be automatically timed + * @param autoTimeRequestsPercentiles default percentiles if requests are auto timed + * @param autoTimeRequestsHistogram default histogram flag if requests are auto timed + * @since 2.2.0 + */ + public WebMvcMetricsFilter(MeterRegistry registry, WebMvcTagsProvider tagsProvider, + String metricName, boolean autoTimeRequests, + List autoTimeRequestsPercentiles, boolean autoTimeRequestsHistogram) { + + double[] percentiles = (autoTimeRequestsPercentiles != null) + ? autoTimeRequestsPercentiles.stream().mapToDouble(Double::doubleValue) + .toArray() + : null; + this.registry = registry; this.tagsProvider = tagsProvider; this.metricName = metricName; this.autoTimeRequests = autoTimeRequests; + this.autoTimeRequestsPercentiles = percentiles; + this.autoTimeRequestsHistogram = autoTimeRequestsHistogram; } @Override @@ -154,7 +186,9 @@ private void record(TimingContext timingContext, HttpServletResponse response, handlerObject, exception); if (annotations.isEmpty()) { if (this.autoTimeRequests) { - stop(timerSample, tags, Timer.builder(this.metricName)); + stop(timerSample, tags, Timer.builder(this.metricName) + .publishPercentiles(this.autoTimeRequestsPercentiles) + .publishPercentileHistogram(this.autoTimeRequestsHistogram)); } } else { diff --git a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizerTests.java b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizerTests.java index 00b9a5361cd9..1c7c01fc9331 100644 --- a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizerTests.java +++ b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/client/MetricsRestTemplateCustomizerTests.java @@ -58,7 +58,8 @@ public void setup() { this.restTemplate = new RestTemplate(); this.mockServer = MockRestServiceServer.createServer(this.restTemplate); this.customizer = new MetricsRestTemplateCustomizer(this.registry, - new DefaultRestTemplateExchangeTagsProvider(), "http.client.requests"); + new DefaultRestTemplateExchangeTagsProvider(), "http.client.requests", + true, null, false); this.customizer.customize(this.restTemplate); } diff --git a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilterTests.java b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilterTests.java index 83bca94ed80e..fc09bce730f1 100644 --- a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilterTests.java +++ b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/reactive/server/MetricsWebFilterTests.java @@ -50,7 +50,8 @@ public void setup() { MockClock clock = new MockClock(); this.registry = new SimpleMeterRegistry(SimpleConfig.DEFAULT, clock); this.webFilter = new MetricsWebFilter(this.registry, - new DefaultWebFluxTagsProvider(), REQUEST_METRICS_NAME, true); + new DefaultWebFluxTagsProvider(), REQUEST_METRICS_NAME, true, null, + false); } @Test diff --git a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterAutoTimedTests.java b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterAutoTimedTests.java index b73f4b5d6ab6..df84c90372f7 100644 --- a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterAutoTimedTests.java +++ b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterAutoTimedTests.java @@ -16,9 +16,13 @@ package org.springframework.boot.actuate.metrics.web.servlet; +import java.util.Arrays; + import io.micrometer.core.instrument.Clock; import io.micrometer.core.instrument.MeterRegistry; import io.micrometer.core.instrument.MockClock; +import io.micrometer.core.instrument.Timer; +import io.micrometer.core.instrument.distribution.HistogramSnapshot; import io.micrometer.core.instrument.simple.SimpleConfig; import io.micrometer.core.instrument.simple.SimpleMeterRegistry; import org.junit.Before; @@ -48,6 +52,7 @@ * Test for {@link WebMvcMetricsFilter} with auto-timed enabled. * * @author Jon Schneider + * @author Tadaya Tsuyukubo */ @RunWith(SpringRunner.class) @WebAppConfiguration @@ -73,8 +78,13 @@ public void setupMockMvc() { @Test public void metricsCanBeAutoTimed() throws Exception { this.mvc.perform(get("/api/10")).andExpect(status().isOk()); - assertThat(this.registry.get("http.server.requests").tags("status", "200").timer() - .count()).isEqualTo(1L); + Timer timer = this.registry.get("http.server.requests").tags("status", "200") + .timer(); + assertThat(timer.count()).isEqualTo(1L); + HistogramSnapshot snapshot = timer.takeSnapshot(); + assertThat(snapshot.percentileValues()).hasSize(2); + assertThat(snapshot.percentileValues()[0].percentile()).isEqualTo(0.5); + assertThat(snapshot.percentileValues()[1].percentile()).isEqualTo(0.95); } @Configuration(proxyBeanMethods = false) @@ -96,7 +106,7 @@ MeterRegistry meterRegistry(Clock clock) { public WebMvcMetricsFilter webMetricsFilter(WebApplicationContext context, MeterRegistry registry) { return new WebMvcMetricsFilter(registry, new DefaultWebMvcTagsProvider(), - "http.server.requests", true); + "http.server.requests", true, Arrays.asList(0.5, 0.95), true); } } diff --git a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterTests.java b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterTests.java index 07b375fcd854..641af1631016 100644 --- a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterTests.java +++ b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsFilterTests.java @@ -372,7 +372,7 @@ CyclicBarrier completableFutureBarrier() { WebMvcMetricsFilter webMetricsFilter(MeterRegistry registry, WebApplicationContext ctx) { return new WebMvcMetricsFilter(registry, new DefaultWebMvcTagsProvider(), - "http.server.requests", true); + "http.server.requests", true, null, false); } } diff --git a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsIntegrationTests.java b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsIntegrationTests.java index 957b6dbd9dab..a30abc38effb 100644 --- a/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsIntegrationTests.java +++ b/spring-boot-project/spring-boot-actuator/src/test/java/org/springframework/boot/actuate/metrics/web/servlet/WebMvcMetricsIntegrationTests.java @@ -111,7 +111,7 @@ MeterRegistry meterRegistry(Clock clock) { public WebMvcMetricsFilter webMetricsFilter(MeterRegistry registry, WebApplicationContext ctx) { return new WebMvcMetricsFilter(registry, new DefaultWebMvcTagsProvider(), - "http.server.requests", true); + "http.server.requests", true, null, false); } @Configuration(proxyBeanMethods = false) 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 0811ac17a3fe..89734a0f2006 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 @@ -1801,7 +1801,7 @@ application's absolute start time [[production-ready-metrics-spring-mvc]] ==== Spring MVC Metrics Auto-configuration enables the instrumentation of requests handled by Spring MVC. When -`management.metrics.web.server.auto-time-requests` is `true`, this instrumentation occurs +`management.metrics.web.server.request.auto-time.enabled` 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: @@ -1896,7 +1896,7 @@ 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.web.server.auto-time-requests` is `true`, this +implementation. When `management.metrics.web.server.request.auto-time.enabled` 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: