My goal is to instrument a Jersey client to collect data on HTTP response/execution time, and I had thought I had the right approach by implementing a JAX-RS ClientRequestFilter
and a ClientResponseFilter
with code in each to record the start and end of the request. However when used with code like the following:
InputStream is = client.target("https://mytarget")
.request(MediaType.APPLICATION_OCTET_STREAM).get(InputStream.class));
// Actually consume the stream, which seems to block waiting for data
final byte[] bytes = IOUtils.toByteArray(is);
... I experience a significant problem as I only end up measuring what appears to be time to header download, and do not measure time it takes to download the entire entity which seems to be happen as I convert the input stream to a byte array (just an example, in my case I am reading the entity contents as they become available).
My use case is to instrument it for use with a distributed tracer (AWS X-Ray). An alternative I had considered was to use a library for Apache HttpClient for this purpose, but that would require changing the default transport layer for Jersey which seemed like an extreme modification to fix a simple problem. (This is slightly more straightforward with RESTEasy since it does appear to use Apache HttpClient by default so with RESTEasy I might have gone that route.)
Is it possible with Jersey to set up a filter that executes when the last byte is written to the entity? Or is there a better way to go about instrumenting a Jersey client?