I am working on the migration of the metrics of our app from the old APIs relying on WebMvcMetricsFilter to the new one, based on Micrometer 1.11, because we are migrating from Spring Boot 2.7.14 to 3.1.4.
Our previous metrics setup was as follows:
Before we were using a filter implementing WebMvcMetricsFilter
:
public class AppWebMvcTimersFilter extends WebMvcMetricsFilter {
private final Predicate<String> predicate;
public AppWebMvcTimersFilter(
final MeterRegistry registry,
final WebMvcTagsProvider tagsProvider,
final String metricName,
final AutoTimer autoTimer,
final Predicate<String> predicate) {
super(registry, tagsProvider, metricName, autoTimer);
this.predicate = predicate;
}
@Override
protected boolean shouldNotFilter(HttpServletRequest request) {
return predicate.test(request.getRequestURI());
}
}
Then we had our implementation of AutoTimer
defining our own buckets, like so:
public class AppMetricAutoTimer implements AutoTimer {
@Override
public void apply(Timer.Builder builder) {
builder
.minimumExpectedValue(Duration.ofMillis(BUCKET_0))
.maximumExpectedValue(Duration.ofMillis(BUCKET_10))
.sla(
Duration.ofMillis(BUCKET_0),
Duration.ofMillis(BUCKET_1),
Duration.ofMillis(BUCKET_2),
Duration.ofMillis(BUCKET_3),
Duration.ofMillis(BUCKET_4),
Duration.ofMillis(BUCKET_5),
Duration.ofMillis(BUCKET_6),
Duration.ofMillis(BUCKET_7),
Duration.ofMillis(BUCKET_8),
Duration.ofMillis(BUCKET_9),
Duration.ofMillis(BUCKET_10));
}
}
And the two things bond in a Metrics configuration class to declare the beans:
@Configuration
public class AppMetricsConfiguration {
@Bean
MeterRegistry appSimpleMeterRegistry() {
return new AppSimpleMeterRegistry(aggregatedTotalLatenciesLoader());
}
@Bean
AutoTimer appMetricAutoTimer() {
return new AppMetricAutoTimer();
}
@Bean
WebMvcTagsProvider appWebMvcTagsProvider() {
return new AppWebMvcTagsProvider();
}
@Bean
WebMvcMetricsFilter appWebMvcTimerFilter(
final MeterRegistry registry,
final WebMvcTagsProvider metricWebMvcTagsProvider,
final AutoTimer appAutoTimer) {
return new AppWebMvcTimersFilter(
registry,
metricWebMvcTagsProvider,
METRIC_FULL_NAME,
appAutoTimer,
uri -> !uri.startsWith(URI_API_PREFIX));
}
}
With the change of Observation APIS in Spring 6:
Now I've got rid of the WebMvcMetricsFilter
. As before, we are configuring an interceptor to use a MeterRegistry
to handle the different counters. But due to the removal of our implementation of WebMvcMetricsFilter
, all of our tests verifying the latencies are now failing.
I haven't found in the documentation any way to provide a bean of AutoTimer
to have the latencies sorted as per our configured buckets.
The question is: how is it supposed now to provide an AutoTimer
in a similar way it was done before in the implementations of WebMvcMetricsFilter
?
AutoTimer is not used anymore, if you want to modify your meters, you can either:
Please check the docs.
Please check the boot and the micrometer docs.