I'm trying to get the metrics (dns resolver time, tls handshake time...) associated to a single request and correlate the metrics with the response.
The purpose is to do a http request, process the response and store somewhere the status and the metrics of the requests.
HttpClientMetricsHandler
and HttpClientMetricsRecorder
are recording the metrics globally. It does not seems applicable.
I have started to look at redoing (but per request) what HttpClientMetricsHandler
is doing and registering the custom handler by calling:
HttpClient httpClient = HttpClient.create().doOnChannelInit(...)
The metrics of the request might be stored as an attribute of the channel and retrived by doing:
httpClient.get().responseConnection((httpClientResponse, connection) -> {
connection.channel().attr()
});
It seems complex and I don't know if it is the best way to achieve my goals. Is there something simpler?
EDIT
I ended up using the Context API
HttpClient httpClient = HttpClient
.create()
.doOnChannelInit((connectionObserver, channel, remoteAddress) -> {
// Get the metrics bean from the context and propagate to the metrics handler
Metrics metrics = connectionObserver.currentContext().get("metrics");
channel.pipeline().addAfter(NettyPipeline.ReactiveBridge,
NettyPipeline.HttpMetricsHandler, new HttpClientMetricsHandler(metrics));
});
httpClient.get()
.response()
.map(httpClientResponse -> {
// Get the metrics bean tied with the response
Metrics metrics = httpClientResponse.currentContextView().get("metrics");
return true;
})
.contextWrite(ctx -> {
// Add the metrics bean to the context
return ctx.put("metrics", new Metrics());
})
.subscribe();
I'm still not sure it is not right way / best way to do it