monad-metrics-0.2.1.1: A convenient wrapper around EKG metrics

Copyright(c) Matt Parsons 2017
Taylor Fausak 2016
LicenseMIT
Maintainerparsonsmatt@gmail.com
Stabilityexperimental
PortabilityPOSIX
Safe HaskellNone
LanguageHaskell2010

Control.Monad.Metrics

Contents

Description

This module presents an easy interface that you can use to collect metrics about your application. It uses EKG from System.Metrics under the hood and is inspired by Taylor Fausak's blunt application.

This module is designed to be imported qualified.

Synopsis

The Type Class

class Monad m => MonadMetrics m where Source #

A type can be an instance of MonadMetrics if it can provide a Metrics somehow. Commonly, this will be implemented as a ReaderT where some field in the environment is the Metrics data.

  • Since v0.1.0.0

Minimal complete definition

getMetrics

Initializing

This library tends to provide simple functions with plain names and generalized functions with apostrophes. When initializing the metrics, you can use initialize if you don't need fine control over the store, or you can use initializeWith if your application already has a store that it uses.

Likewise, we provide run for the simplest case, and run' for the more complex case where you have some larger type.

The most flexible way to use the library is to implement the MonadMetrics class.

initialize :: IO Metrics Source #

Initializes a Metrics value, creating a new Store for it.

  • Since v0.1.0.0

initializeWith :: Store -> IO Metrics Source #

Initializes a Metrics value with the given Store.

  • Since v0.1.0.0

run :: MonadIO m => ReaderT Metrics m a -> m a Source #

Enhances the base monad with metrics. This works for very simple cases, where you don't have a Reader involved yet. If your stack already has a Reader, then you'll get some annoying type problems with this. Switch over to run', or alternatively, define your own MonadMetrics instance.

  • Since v0.1.0.0

run' :: MonadIO m => (Metrics -> r) -> ReaderT r m a -> m a Source #

Adds metric recording capabilities to the given action. The first parameter is a function which accepts a Metrics value and creates the final r value to be used in the action. This is useful when you have a preexisting ReaderT in your stack, and you want to enhance it with metrics.

data Config = Config { size :: Int, metrics' :: Metrics }

main = runWithMetrics (Config 10) $ do
    num <- asks size
    forM_ [1 .. size] _ -> Metrics.increment "foo"
  • Since v0.1.0.0

Collecting Metrics

As with initialization, the library provides "common case" functions with a plain name and generalized functions with an apostrophe.

Only distribution isn't generalized.

increment :: (MonadIO m, MonadMetrics m) => Text -> m () Source #

Increment the named counter by 1.

  • Since v0.1.0.0

counter :: (MonadIO m, MonadMetrics m) => Text -> Int -> m () Source #

A type specialized version of counter' to avoid ambiguous type errors.

  • Since v0.1.0.0

counter' :: (MonadIO m, MonadMetrics m, Integral int) => Text -> int -> m () Source #

Adds the value to the named Counter.

  • Since v0.1.0.0

gauge :: (MonadIO m, MonadMetrics m) => Text -> Int -> m () Source #

A type specialized version of gauge' to avoid ambiguous types.

  • Since v0.1.0.0

gauge' :: (MonadIO m, MonadMetrics m, Integral int) => Text -> int -> m () Source #

Set the value of the named Gauge.

  • Since v0.1.0.0

distribution :: (MonadIO m, MonadMetrics m) => Text -> Double -> m () Source #

Add the value to the named Distribution.

  • Since v0.1.0.0

timed :: (MonadIO m, MonadMetrics m, MonadMask m) => Text -> m a -> m a Source #

Record the time of executing the given action in seconds. Defers to timed'.

  • Since v0.1.0.0

timed' :: (MonadIO m, MonadMetrics m, MonadMask m) => Resolution -> Text -> m a -> m a Source #

Record the time taken to perform the named action. The number is stored in a Distribution and is converted to the specified Resolution.

  • Since v0.1.0.0

timedList :: (MonadIO m, MonadMetrics m, MonadMask m) => Resolution -> [Text] -> m a -> m a Source #

Record the time taken to perform the action, under several names at once. The number is stored in a Distribution and is converted to the specified Resolution.

This is useful to store the same durations data sectioned by different criteria, e.g.:

timedList Seconds ["request.byUser." <> userName, "request.byType." <> requestType] $ do
    ...

So you will have "request.byUser.someuser" storing duration distribution for requests of user "someuser" of any type; and "request.byType.sometype" storing duration distribution for requests of type "sometype" from any user.

label :: (MonadIO m, MonadMetrics m) => Text -> Text -> m () Source #

Set the Label to the given Text value.

  • Since v0.1.0.0

label' :: (MonadIO m, MonadMetrics m, Show a) => Text -> a -> m () Source #

Set the Label to the Shown value of whatever you pass in.

  • Since v0.1.0.0

The Metrics Type

The Metric type contains an IORef to a HashMap from Text labels to the various counters, and a Store to register them with. If you must use the Metric value directly, then you are recommended to use the lenses provided for compatibility.

data Metrics Source #

A container for metrics used by the MonadMetrics class.

  • Since v0.1.0.0

metricsCounters :: Lens' Metrics (IORef (HashMap Text Counter)) Source #

A lens into the Counters provided by the Metrics.

  • Since v0.1.0.0

metricsGauges :: Lens' Metrics (IORef (HashMap Text Gauge)) Source #

A lens into the Gauges provided by the Metrics.

  • Since v0.1.0.0

metricsLabels :: Lens' Metrics (IORef (HashMap Text Label)) Source #

A lens into the Labels provided by the Metrics.

  • Since v0.1.0.0

metricsStore :: Lens' Metrics Store Source #

A lens into the Store provided by the Metrics.

  • Since v0.1.0.0