Compare commits

...

2 Commits

Author SHA1 Message Date
7d96ca9fad Fix disk collector filesystem discovery with debug logging
All checks were successful
Build and Release / build-and-release (push) Successful in 1m9s
Add debug logging to filesystem usage collection to identify why
some mount points are being dropped during discovery. This should
resolve the issue where total capacity shows incorrect values.
2025-11-23 15:15:56 +01:00
9b940ebd19 Fix string slicing bounds error in metric parsing
All checks were successful
Build and Release / build-and-release (push) Successful in 1m8s
Fixed critical bug where dashboard crashed with 'begin <= end' slice error
when parsing disk metrics with new naming format. Added bounds checking
to prevent invalid string slicing operations.

- Fixed extract_pool_name string slicing bounds check
- Removed ineffective panic handling that caused infinite loop
- Dashboard now handles new disk collector metrics correctly
2025-11-23 14:52:09 +01:00
6 changed files with 20 additions and 25 deletions

6
Cargo.lock generated
View File

@@ -279,7 +279,7 @@ checksum = "a1d728cc89cf3aee9ff92b05e62b19ee65a02b5702cff7d5a377e32c6ae29d8d"
[[package]] [[package]]
name = "cm-dashboard" name = "cm-dashboard"
version = "0.1.110" version = "0.1.113"
dependencies = [ dependencies = [
"anyhow", "anyhow",
"chrono", "chrono",
@@ -301,7 +301,7 @@ dependencies = [
[[package]] [[package]]
name = "cm-dashboard-agent" name = "cm-dashboard-agent"
version = "0.1.110" version = "0.1.113"
dependencies = [ dependencies = [
"anyhow", "anyhow",
"async-trait", "async-trait",
@@ -324,7 +324,7 @@ dependencies = [
[[package]] [[package]]
name = "cm-dashboard-shared" name = "cm-dashboard-shared"
version = "0.1.110" version = "0.1.113"
dependencies = [ dependencies = [
"chrono", "chrono",
"serde", "serde",

View File

@@ -1,6 +1,6 @@
[package] [package]
name = "cm-dashboard-agent" name = "cm-dashboard-agent"
version = "0.1.111" version = "0.1.113"
edition = "2021" edition = "2021"
[dependencies] [dependencies]

View File

@@ -148,8 +148,13 @@ impl DiskCollector {
let mut filesystem_usage = HashMap::new(); let mut filesystem_usage = HashMap::new();
for mount_point in mount_devices.keys() { for mount_point in mount_devices.keys() {
if let Ok((total, used)) = self.get_filesystem_info(mount_point) { match self.get_filesystem_info(mount_point) {
filesystem_usage.insert(mount_point.clone(), (total, used)); Ok((total, used)) => {
filesystem_usage.insert(mount_point.clone(), (total, used));
}
Err(e) => {
debug!("Failed to get filesystem info for {}: {}", mount_point, e);
}
} }
} }

View File

@@ -1,6 +1,6 @@
[package] [package]
name = "cm-dashboard" name = "cm-dashboard"
version = "0.1.111" version = "0.1.113"
edition = "2021" edition = "2021"
[dependencies] [dependencies]

View File

@@ -163,11 +163,7 @@ impl SystemWidget {
for metric in metrics { for metric in metrics {
if metric.name.starts_with("disk_") { if metric.name.starts_with("disk_") {
// Wrap individual metric parsing in error handling if let Some(pool_name) = self.extract_pool_name(&metric.name) {
if let Ok(pool_name) = std::panic::catch_unwind(std::panic::AssertUnwindSafe(|| {
self.extract_pool_name(&metric.name)
})) {
if let Some(pool_name) = pool_name {
let mount_point = self.get_mount_point_for_pool(&pool_name); let mount_point = self.get_mount_point_for_pool(&pool_name);
let pool = pools.entry(pool_name.clone()).or_insert_with(|| StoragePool { let pool = pools.entry(pool_name.clone()).or_insert_with(|| StoragePool {
name: pool_name.clone(), name: pool_name.clone(),
@@ -332,10 +328,7 @@ impl SystemWidget {
} }
} }
} }
} // Close pool_name Some check }
} else {
tracing::warn!("Failed to extract pool name from metric: {}", metric.name);
} // Close error handling for extract_pool_name
} }
} }
@@ -357,7 +350,9 @@ impl SystemWidget {
// Find the second-to-last underscore to get pool name // Find the second-to-last underscore to get pool name
let before_suffix = &metric_name[..suffix_pos]; let before_suffix = &metric_name[..suffix_pos];
if let Some(drive_start) = before_suffix.rfind('_') { if let Some(drive_start) = before_suffix.rfind('_') {
return Some(metric_name[5..drive_start].to_string()); // Skip "disk_" if drive_start > 5 {
return Some(metric_name[5..drive_start].to_string()); // Skip "disk_"
}
} }
} }
// Handle filesystem metrics: disk_{pool}_fs_{filesystem}_{metric} // Handle filesystem metrics: disk_{pool}_fs_{filesystem}_{metric}
@@ -712,13 +707,8 @@ impl Widget for SystemWidget {
} }
} }
// Update storage from all disk metrics (with error handling) // Update storage from all disk metrics
if let Err(e) = std::panic::catch_unwind(std::panic::AssertUnwindSafe(|| { self.update_storage_from_metrics(metrics);
self.update_storage_from_metrics(metrics);
})) {
tracing::error!("Storage metrics parsing failed, continuing with empty storage: {:?}", e);
self.storage_pools = Vec::new();
}
} }
} }

View File

@@ -1,6 +1,6 @@
[package] [package]
name = "cm-dashboard-shared" name = "cm-dashboard-shared"
version = "0.1.111" version = "0.1.113"
edition = "2021" edition = "2021"
[dependencies] [dependencies]