lscpu: Add option --json

closes #15
This commit is contained in:
Yang Hau
2024-07-25 04:54:17 +08:00
committed by Daniel Hofstetter
parent 07b28d8205
commit 4fc7653e84
5 changed files with 201 additions and 119 deletions

View File

@@ -15,3 +15,5 @@ regex = { workspace = true }
sysinfo = { workspace = true }
uucore = { workspace = true }
clap = { workspace = true }
serde = { workspace = true }
serde_json = { workspace = true }

View File

@@ -5,40 +5,80 @@
use clap::{crate_version, Arg, ArgAction, Command};
use regex::Regex;
use std::fs;
use serde::Serialize;
use std::{fs, str::FromStr};
use sysinfo::System;
use uucore::{error::UResult, format_usage, help_about, help_usage};
mod options {
pub const HEX: &str = "hex";
pub const JSON: &str = "json";
}
const ABOUT: &str = help_about!("lscpu.md");
const USAGE: &str = help_usage!("lscpu.md");
#[derive(Serialize)]
struct CpuInfos {
lscpu: Vec<CpuInfo>,
}
#[derive(Serialize)]
struct CpuInfo {
field: String,
data: String,
}
impl CpuInfos {
fn new() -> CpuInfos {
CpuInfos {
lscpu: Vec::<CpuInfo>::new(),
}
}
fn push(&mut self, field: &str, data: &str) {
let cpu_info = CpuInfo {
field: String::from_str(field).unwrap(),
data: String::from_str(data).unwrap(),
};
self.lscpu.push(cpu_info);
}
fn to_json(&self) -> String {
serde_json::to_string_pretty(self).unwrap()
}
}
#[uucore::main]
pub fn uumain(args: impl uucore::Args) -> UResult<()> {
let matches: clap::ArgMatches = uu_app().try_get_matches_from(args)?;
let system = System::new_all();
let hex = matches.get_flag(options::HEX);
println!("Architecture: {}", get_architecture());
if hex {
println!("CPU(s): 0x{:x}", system.cpus().len());
} else {
println!("CPU(s): {}", system.cpus().len());
}
let system = System::new_all();
let _hex = matches.get_flag(options::HEX);
let json = matches.get_flag(options::JSON);
let mut cpu_infos = CpuInfos::new();
cpu_infos.push("Architecture", &get_architecture());
cpu_infos.push("CPU(s)", &format!("{}", system.cpus().len()));
// Add more CPU information here...
if let Ok(contents) = fs::read_to_string("/proc/cpuinfo") {
let re = Regex::new(r"^model name\s+:\s+(.*)$").unwrap();
// Assuming all CPUs have the same model name
if let Some(cap) = re.captures_iter(&contents).next() {
println!("Model name: {}", &cap[1]);
cpu_infos.push("Model name", &cap[1]);
};
}
Ok(())
}
// More options can be added here
mod options {
pub const HEX: &str = "hex";
if json {
println!("{}", cpu_infos.to_json());
} else {
for elt in cpu_infos.lscpu {
println!("{}: {}", elt.field, elt.data);
}
}
Ok(())
}
fn get_architecture() -> String {
@@ -68,4 +108,15 @@ pub fn uu_app() -> Command {
)
.required(false),
)
.arg(
Arg::new(options::JSON)
.long("json")
.help(
"Use JSON output format for the default summary or extended output \
(see --extended). For backward compatibility, JSON output follows the \
default summary behavior for non-terminals (e.g., pipes) where \
subsections are missing. See also --hierarchic.",
)
.action(ArgAction::SetTrue),
)
}