Metrics Catalogue

This library provides a way to automatically derive a catalogue of metrics from a struct definition. It generates a hierarchical set of modules & metric keys following the same hierarchy from the root struct. This allows users to interact with the metrics without the risk of typos or having to maintain an external list of available metric keys. Additionally, the metrics can also be interacted with directly, without using the metrics framework.

toml [dependencies] metrics-catalogue = "0.1"

Example

```rust use metric_catalogue::{Metrics, Counter, Gauge};

[derive(Catalogue)]

[metric(root)]

struct Foo { mycounter: Counter, mygauge: Gauge, my_bar: Bar, }

[derive(Catalogue)]

struct Bar { my_counter: Counter, } ```

generates the following catalogue of metric keys:

```rust

[allow(noncamelcase_types)]

pub mod catalogue { pub const MYCOUNTER: &str = "mycounter"; pub const MYGAUGE: &str = "mygauge";

#[allow(noncamelcasetypes)] pub mod bar { pub const MYCOUNTER: &str = "bar.my_counter"; } } ```

allowing updates to the relevant metrics without potential typos:

rust fn my_function() { metrics::increment_counter!(catalogue::my_sub::MY_COUNTER); }

Supported metric types

Currently, the following metric types are supported:

Metrics Registry

Adding the Catalogue derivation will implement the Registry trait for all relevant structs:

rust pub trait Registry { /// Find a registered counter under the provided name fn find_counter(&self, name: &str) -> Option<&Counter>; /// Find a registered gauge under the provided name fn find_gauge(&self, name: &str) -> Option<&Gauge>; }

allowing an automatic hierarchical look-up of the generated catalogue.

Metrics recorder

The Catalogue derivation will also implement the [Recorder] trait for the root struct:

rust impl Recorder for Foo { fn register_counter(&self, _key: &Key, _unit: Option<Unit>, _desc: Option<&'static str>) {} fn register_gauge(&self, _key: &Key, _unit: Option<Unit>, _desc: Option<&'static str>) {} fn register_histogram(&self, _key: &Key, _unit: Option<Unit>, _desc: Option<&'static str>) {} fn record_histogram(&self, _key: &Key, _value: f64) {} fn increment_counter(&self, key: &Key, value: u64) { if let Some(metric) = self.find_counter(key.name()) { metric.increment(value); } } fn update_gauge(&self, key: &Key, value: GaugeValue) { if let Some(metric) = self.find_gauge(key.name()) { match value { GaugeValue::Increment(val) => metric.increase(val), GaugeValue::Decrement(val) => metric.decrease(val), GaugeValue::Absolute(val) => metric.set(val), } } } }

Details

License

Copyright 2021 Sam De Roeck

Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.