use clap::Parser;
#[derive(Parser, Debug, Clone)]
#[command(
author,
version,
about = "Diagnose system slowdowns by monitoring performance metrics",
verbatim_doc_comment
)]
pub struct Config {
#[arg(short, long, default_value_t = 5, value_parser = parse_positive_u64)]
pub interval: u64,
#[arg(short = 'c', long, default_value = "metrics.csv")]
pub csv_file: String,
#[arg(short, long, default_value = "/tmp/slowtest.bin")]
pub test_file: String,
#[arg(short, long, default_value_t = 256, value_parser = parse_positive_usize)]
pub file_size_mb: usize,
#[arg(long, default_value_t = 120, value_parser = parse_positive_usize)]
pub history_size: usize,
#[arg(long)]
pub headless: bool,
#[arg(long, verbatim_doc_comment)]
pub io_bench: bool,
}
fn parse_positive_u64(value: &str) -> Result<u64, String> {
let parsed = value
.parse::<u64>()
.map_err(|e| format!("invalid integer: {}", e))?;
if parsed == 0 {
Err("value must be at least 1".to_string())
} else {
Ok(parsed)
}
}
fn parse_positive_usize(value: &str) -> Result<usize, String> {
let parsed = value
.parse::<usize>()
.map_err(|e| format!("invalid integer: {}", e))?;
if parsed == 0 {
Err("value must be at least 1".to_string())
} else {
Ok(parsed)
}
}
#[cfg(test)]
mod tests {
use clap::Parser;
use super::Config;
#[test]
fn rejects_zero_interval() {
assert!(Config::try_parse_from(["cargo-slow", "--interval", "0"]).is_err());
}
#[test]
fn rejects_zero_file_size() {
assert!(Config::try_parse_from(["cargo-slow", "--file-size-mb", "0"]).is_err());
}
#[test]
fn rejects_zero_history_size() {
assert!(Config::try_parse_from(["cargo-slow", "--history-size", "0"]).is_err());
}
}