[TSM.ID].[11031972] PXE : 19 Cangkang -> REAL Implementation (for/if/match/tests)
This commit is contained in:
@@ -1,3 +1,94 @@
|
||||
#![deny(warnings)]
|
||||
// [TSM.ID].[11031972] -- All Rights Reserved. Proprietary & Confidential.
|
||||
pub mod dashboard;
|
||||
//! [TSM.ID].[11031972] -- Platform X Ecosystem
|
||||
//! xcu-tui -- Terminal Dashboard for System Monitoring
|
||||
use std::collections::HashMap;
|
||||
use std::fmt::Write;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum TuiError { RenderFailed(String) }
|
||||
impl std::fmt::Display for TuiError {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { match self { Self::RenderFailed(e) => write!(f, "Render: {e}") } }
|
||||
}
|
||||
impl std::error::Error for TuiError {}
|
||||
|
||||
pub struct Dashboard { panels: Vec<Panel>, width: usize }
|
||||
pub struct Panel { pub title: String, pub content: PanelContent }
|
||||
|
||||
pub enum PanelContent {
|
||||
Table { headers: Vec<String>, rows: Vec<Vec<String>> },
|
||||
BarChart { labels: Vec<String>, values: Vec<f64>, max_val: f64 },
|
||||
KeyValue(Vec<(String, String)>),
|
||||
StatusGrid { items: Vec<(String, bool)> },
|
||||
}
|
||||
|
||||
impl Dashboard {
|
||||
pub fn new(width: usize) -> Self { Self { panels: Vec::new(), width } }
|
||||
pub fn add_panel(&mut self, panel: Panel) { self.panels.push(panel); }
|
||||
|
||||
pub fn render(&self) -> Result<String, TuiError> {
|
||||
let mut out = String::new();
|
||||
for panel in &self.panels {
|
||||
self.render_border(&mut out, &panel.title);
|
||||
match &panel.content {
|
||||
PanelContent::Table { headers, rows } => self.render_table(&mut out, headers, rows),
|
||||
PanelContent::BarChart { labels, values, max_val } => self.render_bars(&mut out, labels, values, *max_val),
|
||||
PanelContent::KeyValue(pairs) => self.render_kv(&mut out, pairs),
|
||||
PanelContent::StatusGrid { items } => self.render_status(&mut out, items),
|
||||
}
|
||||
let _ = writeln!(out, "{}", "═".repeat(self.width));
|
||||
}
|
||||
Ok(out)
|
||||
}
|
||||
|
||||
fn render_border(&self, out: &mut String, title: &str) {
|
||||
let pad = self.width.saturating_sub(title.len() + 4);
|
||||
let _ = writeln!(out, "╔═ {} {}╗", title, "═".repeat(pad));
|
||||
}
|
||||
|
||||
fn render_table(&self, out: &mut String, headers: &[String], rows: &[Vec<String>]) {
|
||||
let _ = writeln!(out, "║ {}", headers.join(" │ "));
|
||||
let _ = writeln!(out, "║ {}", "─".repeat(self.width - 4));
|
||||
for row in rows { let _ = writeln!(out, "║ {}", row.join(" │ ")); }
|
||||
}
|
||||
|
||||
fn render_bars(&self, out: &mut String, labels: &[String], values: &[f64], max_val: f64) {
|
||||
let bar_width = self.width.saturating_sub(20);
|
||||
for (label, &val) in labels.iter().zip(values.iter()) {
|
||||
let filled = if max_val > 0.0 { (val / max_val * bar_width as f64) as usize } else { 0 };
|
||||
let bar: String = "█".repeat(filled.min(bar_width));
|
||||
let empty: String = "░".repeat(bar_width.saturating_sub(filled));
|
||||
let _ = writeln!(out, "║ {:>8} │{}{} {:>6.1}", label, bar, empty, val);
|
||||
}
|
||||
}
|
||||
|
||||
fn render_kv(&self, out: &mut String, pairs: &[(String, String)]) {
|
||||
for (k, v) in pairs { let _ = writeln!(out, "║ {:>16}: {}", k, v); }
|
||||
}
|
||||
|
||||
fn render_status(&self, out: &mut String, items: &[(String, bool)]) {
|
||||
for (name, ok) in items {
|
||||
let icon = if *ok { "●" } else { "○" };
|
||||
let status = if *ok { "ONLINE" } else { "OFFLINE" };
|
||||
let _ = writeln!(out, "║ {} {:>16} [{}]", icon, name, status);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
#[test]
|
||||
fn test_render() {
|
||||
let mut d = Dashboard::new(60);
|
||||
d.add_panel(Panel { title: "CPU".into(), content: PanelContent::BarChart {
|
||||
labels: vec!["alpha".into(), "beta".into(), "gamma".into()],
|
||||
values: vec![45.0, 72.0, 30.0], max_val: 100.0 } });
|
||||
d.add_panel(Panel { title: "Nodes".into(), content: PanelContent::StatusGrid {
|
||||
items: vec![("alpha".into(), true), ("beta".into(), true), ("gamma".into(), false)] } });
|
||||
let output = d.render().unwrap();
|
||||
assert!(output.contains("alpha"));
|
||||
assert!(output.contains("█"));
|
||||
assert!(output.contains("ONLINE"));
|
||||
assert!(output.contains("OFFLINE"));
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user