Search code examples
javaspringspring-bootdropwizardmetrics

Dropwizard Metrics Get Average Items Per REST Request


I would like to use Dropwizard metrics to get the average number of items in a list for each request my spring boot REST controller services. My controller takes in a string which is serialized into a RequestCollection. RequestCollection has a single List<Integer> ids field that consists of a list of ids. I'd like to know what the average number of items in the ids field is across all requests.

Controller

@RestController
@RequestMapping("/api")
public class ApiController {

    private MetricRegistry metricRegistry;

    public ApiController(MetricRegistry metricRegistry) {
        this.metricRegistry = metricRegistry;
    }

    @GetMapping
    public String getFooBarred(
            @RequestParam(value = "params") String requestItem
    ) {
        RequestCollection request = request = new ObjectMapper()
                .registerModule(new JavaTimeModule())
                .readValue(requestItem, RequestCollection.class);

        // Add metric here to metricRegistry for average number of items 
        // in RequestCollection across all requests.
        // RequestCollection has a single property which is a List<Integer> ids

        return "foobar";
    }
}

Here is the RequestCollection class whose ids field I would like to measure across all requests.

RequestCollection

public class RequestCollection {
    private List<Integer> ids;

    public RequestCollection() {
        this.ids = new ArrayList<>();
    }

    public List<Integer> getIds() {
        return ids;
    }
}

Solution

  • Out of the 5 main metric types, Guages, Counters, Histograms, Meters, and Timers, the one that suits your need the best would probably be the Histogram, which "measures the distribution of values in a stream of data: e.g., the number of results returned by a search".

    Histogram itemCount
        = metrics.histogram(MetricRegistry.name(RequestCollection.class, "id-count"));
    

    The in each request, just update the histogram with the count for the collection.

    itemCount.update(collection.getIds().size());
    

    The reporting will give you a few different of statistics, along with the mean, which is what you want

    -- Histograms ----------------------------
    com.example.RequestCollection.id-count
                 count = 100
                   min = 0
                   max = 99
                  mean = 45.47
                stddev = 31.65
                median = 45.00
                  75% <= 73.00
                  95% <= 94.00
                  98% <= 99.00
                  99% <= 99.00
                99.9% <= 99.00