cat_gateway/metrics/
memory.rs1use std::{
4 alloc::System,
5 sync::atomic::{AtomicBool, Ordering},
6 thread,
7};
8
9use memory_stats::{memory_stats, MemoryStats};
10use stats_alloc::{Region, StatsAlloc, INSTRUMENTED_SYSTEM};
11
12use crate::settings::Settings;
13
14#[global_allocator]
18static GLOBAL: &StatsAlloc<System> = &INSTRUMENTED_SYSTEM;
19
20static IS_INITIALIZED: AtomicBool = AtomicBool::new(false);
22
23pub(crate) fn init_metrics_reporter() {
28 if IS_INITIALIZED.swap(true, Ordering::SeqCst) {
29 return;
30 }
31
32 let stats = Region::new(GLOBAL);
33 let api_host_names = Settings::api_host_names().join(",");
34 let service_id = Settings::service_id();
35
36 thread::spawn(move || {
37 loop {
38 {
39 let allocator_stats = stats.change();
40 let mem_stats = memory_stats().unwrap_or({
41 MemoryStats {
42 physical_mem: 0,
43 virtual_mem: 0,
44 }
45 });
46
47 reporter::MEMORY_PHYSICAL_USAGE
48 .with_label_values(&[&api_host_names, service_id])
49 .set(i64::try_from(mem_stats.physical_mem).unwrap_or(-1));
50 reporter::MEMORY_VIRTUAL_USAGE
51 .with_label_values(&[&api_host_names, service_id])
52 .set(i64::try_from(mem_stats.virtual_mem).unwrap_or(-1));
53 reporter::MEMORY_ALLOCATION_COUNT
54 .with_label_values(&[&api_host_names, service_id])
55 .set(i64::try_from(allocator_stats.allocations).unwrap_or(-1));
56 reporter::MEMORY_DEALLOCATION_COUNT
57 .with_label_values(&[&api_host_names, service_id])
58 .set(i64::try_from(allocator_stats.deallocations).unwrap_or(-1));
59 reporter::MEMORY_REALLOCATION_COUNT
60 .with_label_values(&[&api_host_names, service_id])
61 .set(i64::try_from(allocator_stats.reallocations).unwrap_or(-1));
62 reporter::MEMORY_BYTES_ALLOCATED
63 .with_label_values(&[&api_host_names, service_id])
64 .set(i64::try_from(allocator_stats.bytes_allocated).unwrap_or(-1));
65 reporter::MEMORY_BYTES_DEALLOCATED
66 .with_label_values(&[&api_host_names, service_id])
67 .set(i64::try_from(allocator_stats.bytes_deallocated).unwrap_or(-1));
68 reporter::MEMORY_BYTES_REALLOCATED
69 .with_label_values(&[&api_host_names, service_id])
70 .set(i64::try_from(allocator_stats.bytes_reallocated).unwrap_or(-1));
71 }
72
73 thread::sleep(Settings::metrics_memory_interval());
74 }
75 });
76}
77
78mod reporter {
81 use std::sync::LazyLock;
82
83 use prometheus::{register_int_gauge_vec, IntGaugeVec};
84
85 const MEMORY_METRIC_LABELS: [&str; 2] = ["api_host_names", "service_id"];
87
88 pub(super) static MEMORY_PHYSICAL_USAGE: LazyLock<IntGaugeVec> = LazyLock::new(|| {
90 register_int_gauge_vec!(
91 "memory_physical_usage",
92 "Amount of physical memory usage in bytes",
93 &MEMORY_METRIC_LABELS
94 )
95 .unwrap()
96 });
97
98 pub(super) static MEMORY_VIRTUAL_USAGE: LazyLock<IntGaugeVec> = LazyLock::new(|| {
100 register_int_gauge_vec!(
101 "memory_virtual_usage",
102 "Amount of physical virtual usage in bytes",
103 &MEMORY_METRIC_LABELS
104 )
105 .unwrap()
106 });
107
108 pub(super) static MEMORY_ALLOCATION_COUNT: LazyLock<IntGaugeVec> = LazyLock::new(|| {
110 register_int_gauge_vec!(
111 "memory_allocation_count",
112 "Number of allocation count in the heap",
113 &MEMORY_METRIC_LABELS
114 )
115 .unwrap()
116 });
117
118 pub(super) static MEMORY_DEALLOCATION_COUNT: LazyLock<IntGaugeVec> = LazyLock::new(|| {
120 register_int_gauge_vec!(
121 "memory_deallocation_count",
122 "Number of deallocation count in the heap",
123 &MEMORY_METRIC_LABELS
124 )
125 .unwrap()
126 });
127
128 pub(super) static MEMORY_REALLOCATION_COUNT: LazyLock<IntGaugeVec> = LazyLock::new(|| {
130 register_int_gauge_vec!(
131 "memory_reallocation_count",
132 "Number of reallocation count in the heap",
133 &MEMORY_METRIC_LABELS
134 )
135 .unwrap()
136 });
137
138 pub(super) static MEMORY_BYTES_ALLOCATED: LazyLock<IntGaugeVec> = LazyLock::new(|| {
140 register_int_gauge_vec!(
141 "memory_bytes_allocated",
142 "Amount of accumulative allocated bytes in the heap",
143 &MEMORY_METRIC_LABELS
144 )
145 .unwrap()
146 });
147
148 pub(super) static MEMORY_BYTES_DEALLOCATED: LazyLock<IntGaugeVec> = LazyLock::new(|| {
150 register_int_gauge_vec!(
151 "memory_bytes_deallocated",
152 "Amount of accumulative deallocated bytes in the heap",
153 &MEMORY_METRIC_LABELS
154 )
155 .unwrap()
156 });
157
158 pub(super) static MEMORY_BYTES_REALLOCATED: LazyLock<IntGaugeVec> = LazyLock::new(|| {
160 register_int_gauge_vec!(
161 "memory_bytes_reallocated",
162 "Amount of accumulative reallocated bytes in the heap",
163 &MEMORY_METRIC_LABELS
164 )
165 .unwrap()
166 });
167}