relay_utils/metrics/
global.rs1use crate::metrics::{
20 metric_name, register, Gauge, GaugeVec, Metric, Opts, PrometheusError, Registry,
21 StandaloneMetric, F64, U64,
22};
23
24use async_std::sync::{Arc, Mutex};
25use async_trait::async_trait;
26use std::time::Duration;
27use sysinfo::{RefreshKind, System};
28
29const UPDATE_INTERVAL: Duration = Duration::from_secs(10);
31
32#[derive(Debug, Clone)]
34pub struct GlobalMetrics {
35 system: Arc<Mutex<System>>,
36 system_average_load: GaugeVec<F64>,
37 process_cpu_usage_percentage: Gauge<F64>,
38 process_memory_usage_bytes: Gauge<U64>,
39}
40
41impl GlobalMetrics {
42 pub fn new() -> Result<Self, PrometheusError> {
44 Ok(GlobalMetrics {
45 system: Arc::new(Mutex::new(System::new_with_specifics(RefreshKind::everything()))),
46 system_average_load: GaugeVec::new(
47 Opts::new(metric_name(None, "system_average_load"), "System load average"),
48 &["over"],
49 )?,
50 process_cpu_usage_percentage: Gauge::new(
51 metric_name(None, "process_cpu_usage_percentage"),
52 "Process CPU usage",
53 )?,
54 process_memory_usage_bytes: Gauge::new(
55 metric_name(None, "process_memory_usage_bytes"),
56 "Process memory (resident set size) usage",
57 )?,
58 })
59 }
60}
61
62impl Metric for GlobalMetrics {
63 fn register(&self, registry: &Registry) -> Result<(), PrometheusError> {
64 register(self.system_average_load.clone(), registry)?;
65 register(self.process_cpu_usage_percentage.clone(), registry)?;
66 register(self.process_memory_usage_bytes.clone(), registry)?;
67 Ok(())
68 }
69}
70
71#[async_trait]
72impl StandaloneMetric for GlobalMetrics {
73 async fn update(&self) {
74 let mut system = self.system.lock().await;
76 let load = sysinfo::System::load_average();
77 self.system_average_load.with_label_values(&["1min"]).set(load.one);
78 self.system_average_load.with_label_values(&["5min"]).set(load.five);
79 self.system_average_load.with_label_values(&["15min"]).set(load.fifteen);
80
81 let pid = sysinfo::get_current_pid().expect(
83 "only fails where pid is unavailable (os=unknown || arch=wasm32);\
84 relay is not supposed to run in such MetricsParamss;\
85 qed",
86 );
87 let is_process_refreshed = system.refresh_process(pid);
88 match (is_process_refreshed, system.process(pid)) {
89 (true, Some(process_info)) => {
90 let cpu_usage = process_info.cpu_usage() as f64;
91 let memory_usage = process_info.memory() * 1024;
92 log::trace!(
93 target: "bridge-metrics",
94 "Refreshed process metrics: CPU={}, memory={}",
95 cpu_usage,
96 memory_usage,
97 );
98
99 self.process_cpu_usage_percentage.set(if cpu_usage.is_finite() {
100 cpu_usage
101 } else {
102 0f64
103 });
104 self.process_memory_usage_bytes.set(memory_usage);
105 },
106 _ => {
107 log::warn!(
108 target: "bridge-metrics",
109 "Failed to refresh process information. Metrics may show obsolete values",
110 );
111 },
112 }
113 }
114
115 fn update_interval(&self) -> Duration {
116 UPDATE_INTERVAL
117 }
118}