Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor(layers/prometheus-client): provide builder APIs #5073

Merged
Prev Previous commit
Next Next commit
improve builder
koushiro committed Sep 3, 2024
commit 9bd88f3f24fd95db0a60d4c2fd12b17e14f02f34
69 changes: 35 additions & 34 deletions core/src/layers/prometheus_client.rs
Original file line number Diff line number Diff line change
@@ -100,38 +100,20 @@ impl<A: Access> Layer<A> for PrometheusClientLayer {
}
}

#[derive(Clone)]
struct HistogramConstructor {
buckets: Vec<f64>,
}

impl MetricConstructor<Histogram> for HistogramConstructor {
fn new_metric(&self) -> Histogram {
Histogram::new(self.buckets.iter().cloned())
}
}

/// [`PrometheusClientLayerBuilder`] is a config builder to build a [`PrometheusClientLayer`].
pub struct PrometheusClientLayerBuilder {
operation_duration_seconds: Family<OperationLabels, Histogram, HistogramConstructor>,
operation_bytes: Family<OperationLabels, Histogram, HistogramConstructor>,
operation_errors_total: Family<OperationLabels, Counter>,
operation_duration_seconds_buckets: Vec<f64>,
operation_bytes_buckets: Vec<f64>,
path_label_level: usize,
}

impl Default for PrometheusClientLayerBuilder {
fn default() -> Self {
let operation_duration_seconds = Family::new_with_constructor(HistogramConstructor {
buckets: exponential_buckets(0.01, 2.0, 16).collect(),
});
let operation_bytes = Family::new_with_constructor(HistogramConstructor {
buckets: exponential_buckets(1.0, 2.0, 16).collect(),
});
let operation_errors_total = Family::<OperationLabels, Counter>::default();
let operation_duration_seconds_buckets = exponential_buckets(0.01, 2.0, 16).collect();
let operation_bytes_buckets = exponential_buckets(1.0, 2.0, 16).collect();
Self {
operation_duration_seconds,
operation_bytes,
operation_errors_total,
operation_duration_seconds_buckets,
operation_bytes_buckets,
path_label_level: 0,
}
}
@@ -171,8 +153,7 @@ impl PrometheusClientLayerBuilder {
/// ```
pub fn operation_duration_seconds_buckets(mut self, buckets: Vec<f64>) -> Self {
if !buckets.is_empty() {
let constructor = HistogramConstructor { buckets };
self.operation_duration_seconds = Family::<_, _, _>::new_with_constructor(constructor);
self.operation_duration_seconds_buckets = buckets;
}
self
}
@@ -210,8 +191,7 @@ impl PrometheusClientLayerBuilder {
/// ```
pub fn operation_bytes_buckets(mut self, buckets: Vec<f64>) -> Self {
if !buckets.is_empty() {
let constructor = HistogramConstructor { buckets };
self.operation_bytes = Family::<_, _, _>::new_with_constructor(constructor);
self.operation_bytes_buckets = buckets;
}
self
}
@@ -282,35 +262,56 @@ impl PrometheusClientLayerBuilder {
/// # }
/// ```
pub fn register(self, registry: &mut Registry) -> PrometheusClientLayer {
let operation_duration_seconds =
Family::<OperationLabels, _, _>::new_with_constructor(HistogramConstructor {
buckets: self.operation_duration_seconds_buckets,
});
let operation_bytes =
Family::<OperationLabels, _, _>::new_with_constructor(HistogramConstructor {
buckets: self.operation_bytes_buckets,
});
let operation_errors_total = Family::<OperationLabels, Counter>::default();

registry.register(
observe::METRIC_OPERATION_DURATION_SECONDS.name(),
observe::METRIC_OPERATION_DURATION_SECONDS.help(),
self.operation_duration_seconds.clone(),
operation_duration_seconds.clone(),
);
registry.register(
observe::METRIC_OPERATION_BYTES.name(),
observe::METRIC_OPERATION_BYTES.help(),
self.operation_bytes.clone(),
operation_bytes.clone(),
);
// `prometheus-client` will automatically add `_total` suffix into the name of counter
// metrics, so we can't use `METRIC_OPERATION_ERRORS_TOTAL.name()` here.
registry.register(
"opendal_operation_errors",
observe::METRIC_OPERATION_ERRORS_TOTAL.help(),
self.operation_errors_total.clone(),
operation_errors_total.clone(),
);

PrometheusClientLayer {
interceptor: PrometheusClientInterceptor {
operation_duration_seconds: self.operation_duration_seconds,
operation_bytes: self.operation_bytes,
operation_errors_total: self.operation_errors_total,
operation_duration_seconds,
operation_bytes,
operation_errors_total,
path_label_level: self.path_label_level,
},
}
}
}

#[derive(Clone)]
struct HistogramConstructor {
buckets: Vec<f64>,
}

impl MetricConstructor<Histogram> for HistogramConstructor {
fn new_metric(&self) -> Histogram {
Histogram::new(self.buckets.iter().cloned())
}
}

#[derive(Clone, Debug)]
pub struct PrometheusClientInterceptor {
operation_duration_seconds: Family<OperationLabels, Histogram, HistogramConstructor>,