use crate::{datetime::DateTime, extension::JsonObjectExt, LazyLock, Map};
use parking_lot::RwLock;
use sysinfo::{Disks, Networks, System};
pub(super) fn refresh_and_retrieve() -> Map {
refresh_system();
let sys = SHARED_SYSTEM_MONITOR.read();
let mut map = SYSTEM_INFO.clone();
map.upsert("os.uptime", System::uptime());
if System::name().is_some_and(|sys_name| !sys_name.eq_ignore_ascii_case("windows")) {
let load_avg = System::load_average();
let load_avg_values = vec![load_avg.one, load_avg.five, load_avg.fifteen];
map.upsert("os.load_average", load_avg_values);
}
map.upsert("mem.free_memory", sys.free_memory());
map.upsert("mem.available_memory", sys.available_memory());
map.upsert("mem.used_memory", sys.used_memory());
map.upsert("mem.free_swap", sys.free_swap());
map.upsert("mem.used_swap", sys.used_swap());
let disks = Disks::new_with_refreshed_list();
map.upsert(
"disk.available_space",
disks
.list()
.iter()
.fold(0, |sum, disk| sum + disk.available_space()),
);
let mut network_received = 0;
let mut network_total_received = 0;
let mut network_transmitted = 0;
let mut network_total_transmitted = 0;
let mut network_packets_received = 0;
let mut network_total_packets_received = 0;
let mut network_packets_transmitted = 0;
let mut network_total_packets_transmitted = 0;
let mut network_errors_on_received = 0;
let mut network_total_errors_on_received = 0;
let mut network_errors_on_transmitted = 0;
let mut network_total_errors_on_transmitted = 0;
let networks = Networks::new_with_refreshed_list();
for (_name, network) in &networks {
network_received += network.received();
network_total_received += network.total_received();
network_transmitted += network.transmitted();
network_total_transmitted += network.total_transmitted();
network_packets_received += network.packets_received();
network_total_packets_received += network.total_packets_received();
network_packets_transmitted += network.packets_transmitted();
network_total_packets_transmitted += network.total_packets_transmitted();
network_errors_on_received += network.errors_on_received();
network_total_errors_on_received += network.total_errors_on_received();
network_errors_on_transmitted += network.errors_on_transmitted();
network_total_errors_on_transmitted += network.total_errors_on_transmitted();
}
map.upsert("net.received", network_received);
map.upsert("net.total_received", network_total_received);
map.upsert("net.transmitted", network_transmitted);
map.upsert("net.total_transmitted", network_total_transmitted);
map.upsert("net.packets_received", network_packets_received);
map.upsert("net.total_packets_received", network_total_packets_received);
map.upsert("net.packets_transmitted", network_packets_transmitted);
map.upsert(
"net.total_packets_transmitted",
network_total_packets_transmitted,
);
map.upsert("net.errors_on_received", network_errors_on_received);
map.upsert(
"net.total_errors_on_received",
network_total_errors_on_received,
);
map.upsert("net.errors_on_transmitted", network_errors_on_transmitted);
map.upsert(
"net.total_errors_on_transmitted",
network_total_errors_on_transmitted,
);
map
}
fn refresh_system() {
let mut sys = SHARED_SYSTEM_MONITOR.write();
sys.refresh_cpu();
sys.refresh_memory();
}
static SYSTEM_INFO: LazyLock<Map> = LazyLock::new(|| {
let mut map = Map::new();
let mut sys = System::new();
sys.refresh_cpu();
sys.refresh_memory();
map.upsert("os.name", System::name());
map.upsert("os.version", System::os_version());
if let Ok(boot_time) = i64::try_from(System::boot_time()) {
map.upsert("os.booted_at", DateTime::from_timestamp(boot_time));
}
map.upsert("cpu.num_cpus", sys.cpus().len());
map.upsert("cpu.physical_core_count", sys.physical_core_count());
map.upsert("mem.total_memory", sys.total_memory());
map.upsert("mem.total_swap", sys.total_swap());
let disks = Disks::new_with_refreshed_list();
map.upsert(
"disk.total_space",
disks
.list()
.iter()
.fold(0, |sum, disk| sum + disk.total_space()),
);
map
});
static SHARED_SYSTEM_MONITOR: LazyLock<RwLock<System>> =
LazyLock::new(|| RwLock::new(System::new()));