packages feed

monad-metrics 0.2.0.0 → 0.2.1.0

raw patch · 4 files changed

+104/−56 lines, 4 filesdep +exceptionsdep ~basePVP: major bump suggested

API removals or changes: PVP suggests a major version bump

Dependencies added: exceptions

Dependency ranges changed: base

API changes (from Hackage documentation)

+ Control.Monad.Metrics: timedList :: (MonadIO m, MonadMetrics m, MonadMask m) => Resolution -> [Text] -> m a -> m a
- Control.Monad.Metrics: timed :: (MonadIO m, MonadMetrics m) => Text -> m a -> m a
+ Control.Monad.Metrics: timed :: (MonadIO m, MonadMetrics m, MonadMask m) => Text -> m a -> m a
- Control.Monad.Metrics: timed' :: (MonadIO m, MonadMetrics m) => Resolution -> Text -> m a -> m a
+ Control.Monad.Metrics: timed' :: (MonadIO m, MonadMetrics m, MonadMask m) => Resolution -> Text -> m a -> m a

Files

+ CHANGELOG.md view
@@ -0,0 +1,20 @@+# Change Log++## Upcoming...++- Introduced `timedList` method, to store the same distribution data under several names at once.++## v0.2.0.0 ++- Make `timed` and `timed'` require a `MonadMask` constraint for bracketing.+- [#7](https://github.com/sellerlabs/monad-metrics/pull/7) Switch `Map` to `HashMap`; [~4x faster to look up](https://github.com/sellerlabs/monad-metrics/pull/8)+- Fix a potential race condition when registering new metrics.++## v0.1.0.2++Fix bug where timed metrics are reported in the negatives.++## ~~v0.1.0.0~~ v0.1.0.1++Initial Release+
monad-metrics.cabal view
@@ -1,42 +1,50 @@-name:                monad-metrics-version:             0.2.0.0-synopsis:            A convenient wrapper around EKG metrics-description:         A convenient wrapper for collecting application metrics. Please see the README.md for more information.-homepage:            https://github.com/sellerlabs/monad-metrics#readme-license:             MIT-license-file:        LICENSE-author:              Matthew Parsons-maintainer:          matt@sellerlabs.com-copyright:           2017 Seller Labs, 2016 Taylor Fausak-category:            Web-build-type:          Simple-extra-source-files:  README.md-cabal-version:       >=1.10+name: monad-metrics+version: 0.2.1.0+cabal-version: >=1.10+build-type: Simple+license: MIT+license-file: LICENSE+copyright: 2017 Seller Labs, 2016 Taylor Fausak+maintainer: matt@sellerlabs.com+homepage: https://github.com/sellerlabs/monad-metrics#readme+synopsis: A convenient wrapper around EKG metrics+description:+    A convenient wrapper for collecting application metrics. Please see the README.md for more information.+category: Web+author: Matthew Parsons+extra-source-files:+    README.md+    CHANGELOG.md -library-  hs-source-dirs:      src-  exposed-modules:     Control.Monad.Metrics-                     , Control.Monad.Metrics.Internal-  build-depends:       base                 >= 4.7     && < 5-                     , clock                >= 0.3     && < 0.8-                     , ekg-core             >= 0.1.0.1 && < 0.2-                     , hashable             >= 1.2     && < 1.3-                     , text                               < 1.3-                     , mtl                  >= 2       && < 2.3-                     , transformers         >= 0.3     && < 0.6-                     , unordered-containers >= 0.2     && < 0.3-                     , microlens            >= 0.2     && < 0.5-  default-language:    Haskell2010+source-repository head+    type: git+    location: https://github.com/sellerlabs/monad-metrics -test-suite monad-metrics-test-  type:                exitcode-stdio-1.0-  hs-source-dirs:      test-  main-is:             Spec.hs-  build-depends:       base             >= 4.6 && <= 5.0-                     , monad-metrics-  ghc-options:         -threaded -rtsopts -with-rtsopts=-N-  default-language:    Haskell2010+library+    exposed-modules:+        Control.Monad.Metrics+        Control.Monad.Metrics.Internal+    build-depends:+        base >=4.8 && <5,+        clock >=0.3 && <0.8,+        ekg-core >=0.1.0.1 && <0.2,+        exceptions >=0.6 && <0.9,+        hashable ==1.2.*,+        microlens >=0.2 && <0.5,+        mtl >=2 && <2.3,+        text <1.3,+        transformers >=0.3 && <0.6,+        unordered-containers ==0.2.*+    default-language: Haskell2010+    hs-source-dirs: src+    ghc-options: -Wall -source-repository head-  type:     git-  location: https://github.com/sellerlabs/monad-metrics+test-suite  monad-metrics-test+    type: exitcode-stdio-1.0+    main-is: Spec.hs+    build-depends:+        base >=4.8 && <=5.0,+        monad-metrics -any+    default-language: Haskell2010+    hs-source-dirs: test+    ghc-options: -threaded -rtsopts -with-rtsopts=-N
src/Control/Monad/Metrics.hs view
@@ -39,6 +39,7 @@     , distribution     , timed     , timed'+    , timedList     , label     , label'     , Resolution(..)@@ -51,7 +52,8 @@     , metricsStore     ) where -import           Control.Monad                  (liftM)+import           Control.Monad                  (liftM, forM_)+import           Control.Monad.Catch            (MonadMask, bracket) import           Control.Monad.IO.Class         (MonadIO (..)) import           Control.Monad.Reader           (MonadReader (..), ReaderT (..)) import           Control.Monad.Trans            (MonadTrans (..))@@ -63,8 +65,7 @@ import           Data.Monoid                    (mempty) import           Data.Text                      (Text) import qualified Data.Text                      as Text-import           System.Clock                   (Clock (..), TimeSpec (..),-                                                 getTime)+import           System.Clock                   (Clock (..), getTime) import           System.IO.Unsafe               (unsafeInterleaveIO) import qualified System.Metrics                 as EKG import           System.Metrics.Counter         as Counter@@ -203,23 +204,42 @@ gauge = gauge'  -- | Record the time taken to perform the named action. The number is--- stored in a 'System.Metrics.Disribution.Distribution' and is converted+-- stored in a 'System.Metrics.Distribution.Distribution' and is converted -- to the specified 'Resolution'. -- -- * /Since v0.1.0.0/-timed' :: (MonadIO m, MonadMetrics m) => Resolution -> Text -> m a -> m a-timed' resolution name action = do-    start <- liftIO $ getTime Monotonic-    result <- action-    end <- liftIO $ getTime Monotonic-    distribution name (diffTime resolution end start)-    return result+timed' :: (MonadIO m, MonadMetrics m, MonadMask m) => Resolution -> Text -> m a -> m a+timed' resolution name action = timedList resolution [name] action +-- | Record the time taken to perform the action, under several names at once.+-- The number is stored in a 'System.Metrics.Distribution.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.+--+timedList :: (MonadIO m, MonadMetrics m, MonadMask m) => Resolution -> [Text] -> m a -> m a+timedList resolution names action = +    bracket (liftIO (getTime Monotonic)) finish (const action)+  where+    finish start = do+        end <- liftIO (getTime Monotonic)+        forM_ names $ \name ->+            distribution name (diffTime resolution end start)+ -- | Record the time of executing the given action in seconds. Defers to -- 'timed''. -- -- * /Since v0.1.0.0/-timed :: (MonadIO m, MonadMetrics m) => Text -> m a -> m a+timed :: (MonadIO m, MonadMetrics m, MonadMask m) => Text -> m a -> m a timed = timed' Seconds  -- | Set the 'Label' to the given 'Text' value.
src/Control/Monad/Metrics/Internal.hs view
@@ -14,10 +14,10 @@ -} module Control.Monad.Metrics.Internal where -import           Data.IORef import           Data.HashMap.Strict         (HashMap)+import           Data.IORef import           Data.Text                   (Text)-import           Lens.Micro+import           Lens.Micro                  (Lens') import           System.Clock                (TimeSpec (..)) import           System.Metrics              (Store) import           System.Metrics.Counter      (Counter)@@ -82,9 +82,9 @@  diffTime :: Resolution -> TimeSpec -> TimeSpec -> Double diffTime res (TimeSpec seca nseca) (TimeSpec secb nsecb) =-    let secs = seca - secb-        nsecs = nseca - nsecb-     in convertTimeSpecTo res (TimeSpec secs nsecs)+    let sec' = seca - secb+        nsec' = nseca - nsecb+     in convertTimeSpecTo res (TimeSpec sec' nsec')  convertTimeSpecTo :: Resolution -> TimeSpec -> Double convertTimeSpecTo res (TimeSpec secs' nsecs') =