use std::fmt::Write;
use std::fs;
use std::process::Command;
use std::time::{SystemTime, UNIX_EPOCH};
use crate::modules::enums::OsAgeShorthand;
pub fn get_os_age(shorthand: OsAgeShorthand) -> Option<String> {
let install_epoch = read_install_epoch_seconds()?;
let now = SystemTime::now().duration_since(UNIX_EPOCH).ok()?.as_secs();
let seconds = now.saturating_sub(install_epoch);
let days = seconds / 86_400;
let hours = (seconds / 3_600) % 24;
let minutes = (seconds / 60) % 60;
let mut buf = String::with_capacity(32);
match shorthand {
OsAgeShorthand::Full => {
if days > 0 {
write!(buf, "{} day{}, ", days, if days != 1 { "s" } else { "" }).ok()?;
}
if hours > 0 {
write!(buf, "{} hour{}, ", hours, if hours != 1 { "s" } else { "" }).ok()?;
}
if minutes > 0 {
write!(
buf,
"{} minute{}",
minutes,
if minutes != 1 { "s" } else { "" }
)
.ok()?;
}
if buf.is_empty() {
write!(buf, "{} seconds", seconds).ok()?;
}
}
OsAgeShorthand::Tiny => {
if days > 0 {
write!(buf, "{} days", days).ok()?;
}
}
OsAgeShorthand::Seconds => {
write!(buf, "{}s", seconds).ok()?;
}
}
Some(buf.trim_end_matches([' ', ','].as_ref()).to_string())
}
fn read_install_epoch_seconds() -> Option<u64> {
if let Ok(md) = fs::metadata("/") {
if let Ok(created) = md.created() {
if let Ok(dur) = created.duration_since(UNIX_EPOCH) {
let secs = dur.as_secs();
if secs > 0 {
return Some(secs);
}
}
}
}
let out = Command::new("stat").args(["-c", "%W", "/"]).output().ok()?;
if !out.status.success() {
return None;
}
let s = String::from_utf8_lossy(&out.stdout).trim().to_string();
if s == "0" || s == "-1" {
return None;
}
if let Ok(v) = s.parse::<i64>() {
if v > 0 {
return Some(v as u64);
}
}
None
}