refactor: combine process column code (#1622)

* rename some files

* refactor: combine process column code

* rename some and sort the schema columns
This commit is contained in:
Clement Tsang 2024-11-14 05:24:24 -05:00 committed by GitHub
parent 103c4f6ab4
commit 6d37d5756f
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
6 changed files with 169 additions and 212 deletions

View file

@ -674,32 +674,31 @@
} }
}, },
"ProcColumn": { "ProcColumn": {
"description": "A column in the process widget.",
"type": "string", "type": "string",
"enum": [ "enum": [
"PID",
"Count",
"Name",
"Command",
"CPU%", "CPU%",
"Command",
"Count",
"GMem",
"GMem%",
"GPU%",
"Mem", "Mem",
"Mem%", "Mem%",
"Name",
"PID",
"R/s", "R/s",
"Read", "Read",
"Rps", "Rps",
"W/s", "State",
"Write",
"Wps",
"T.Read", "T.Read",
"TWrite",
"T.Write", "T.Write",
"TRead", "TRead",
"State", "TWrite",
"User",
"Time", "Time",
"GMem", "User",
"GMem%", "W/s",
"GPU%" "Wps",
"Write"
] ]
}, },
"ProcessesConfig": { "ProcessesConfig": {

View file

@ -283,9 +283,10 @@ fn generate_schema() -> anyhow::Result<()> {
match proc_columns { match proc_columns {
schemars::schema::Schema::Object(proc_columns) => { schemars::schema::Schema::Object(proc_columns) => {
let enums = proc_columns.enum_values.as_mut().unwrap(); let enums = proc_columns.enum_values.as_mut().unwrap();
*enums = options::config::process::ProcColumn::VARIANTS *enums = widgets::ProcColumn::VARIANTS
.iter() .iter()
.flat_map(|var| var.get_schema_names()) .flat_map(|var| var.get_schema_names())
.sorted()
.map(|v| serde_json::Value::String(v.to_string())) .map(|v| serde_json::Value::String(v.to_string()))
.dedup() .dedup()
.collect(); .collect();

View file

@ -1,6 +1,6 @@
use serde::Deserialize; use serde::Deserialize;
use crate::widgets::ProcWidgetColumn; use crate::widgets::ProcColumn;
/// Process configuration. /// Process configuration.
#[derive(Clone, Debug, Default, Deserialize)] #[derive(Clone, Debug, Default, Deserialize)]
@ -12,116 +12,6 @@ pub struct ProcessesConfig {
pub columns: Vec<ProcColumn>, pub columns: Vec<ProcColumn>,
} }
/// A column in the process widget.
#[derive(Clone, Debug)]
#[cfg_attr(
feature = "generate_schema",
derive(schemars::JsonSchema, strum::VariantArray)
)]
#[cfg_attr(test, derive(PartialEq, Eq))]
pub enum ProcColumn {
Pid,
Count,
Name,
Command,
CpuPercent,
Mem,
MemPercent,
Read,
Write,
TotalRead,
TotalWrite,
State,
User,
Time,
#[cfg(feature = "gpu")]
GpuMem,
#[cfg(feature = "gpu")]
GpuPercent,
}
impl ProcColumn {
/// An ugly hack to generate the JSON schema.
#[cfg(feature = "generate_schema")]
pub fn get_schema_names(&self) -> &[&'static str] {
match self {
ProcColumn::Pid => &["PID"],
ProcColumn::Count => &["Count"],
ProcColumn::Name => &["Name"],
ProcColumn::Command => &["Command"],
ProcColumn::CpuPercent => &["CPU%"],
ProcColumn::Mem => &["Mem"],
ProcColumn::MemPercent => &["Mem%"],
ProcColumn::Read => &["R/s", "Read", "Rps"],
ProcColumn::Write => &["W/s", "Write", "Wps"],
ProcColumn::TotalRead => &["T.Read", "TWrite"],
ProcColumn::TotalWrite => &["T.Write", "TRead"],
ProcColumn::State => &["State"],
ProcColumn::User => &["User"],
ProcColumn::Time => &["Time"],
#[cfg(feature = "gpu")]
ProcColumn::GpuMem => &["GMem", "GMem%"],
#[cfg(feature = "gpu")]
ProcColumn::GpuPercent => &["GPU%"],
}
}
}
impl<'de> Deserialize<'de> for ProcColumn {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: serde::Deserializer<'de>,
{
let value = String::deserialize(deserializer)?.to_lowercase();
match value.as_str() {
"cpu%" => Ok(ProcColumn::CpuPercent),
"mem" => Ok(ProcColumn::Mem),
"mem%" => Ok(ProcColumn::Mem),
"pid" => Ok(ProcColumn::Pid),
"count" => Ok(ProcColumn::Count),
"name" => Ok(ProcColumn::Name),
"command" => Ok(ProcColumn::Command),
"read" | "r/s" | "rps" => Ok(ProcColumn::Read),
"write" | "w/s" | "wps" => Ok(ProcColumn::Write),
"tread" | "t.read" => Ok(ProcColumn::TotalRead),
"twrite" | "t.write" => Ok(ProcColumn::TotalWrite),
"state" => Ok(ProcColumn::State),
"user" => Ok(ProcColumn::User),
"time" => Ok(ProcColumn::Time),
#[cfg(feature = "gpu")]
"gmem" | "gmem%" => Ok(ProcColumn::GpuMem),
#[cfg(feature = "gpu")]
"gpu%" => Ok(ProcColumn::GpuPercent),
_ => Err(serde::de::Error::custom("doesn't match any column type")),
}
}
}
impl From<&ProcColumn> for ProcWidgetColumn {
fn from(value: &ProcColumn) -> Self {
match value {
ProcColumn::Pid => ProcWidgetColumn::PidOrCount,
ProcColumn::Count => ProcWidgetColumn::PidOrCount,
ProcColumn::Name => ProcWidgetColumn::ProcNameOrCommand,
ProcColumn::Command => ProcWidgetColumn::ProcNameOrCommand,
ProcColumn::CpuPercent => ProcWidgetColumn::Cpu,
ProcColumn::Mem => ProcWidgetColumn::Mem,
ProcColumn::MemPercent => ProcWidgetColumn::Mem,
ProcColumn::Read => ProcWidgetColumn::ReadPerSecond,
ProcColumn::Write => ProcWidgetColumn::WritePerSecond,
ProcColumn::TotalRead => ProcWidgetColumn::TotalRead,
ProcColumn::TotalWrite => ProcWidgetColumn::TotalWrite,
ProcColumn::State => ProcWidgetColumn::State,
ProcColumn::User => ProcWidgetColumn::User,
ProcColumn::Time => ProcWidgetColumn::Time,
#[cfg(feature = "gpu")]
ProcColumn::GpuMem => ProcWidgetColumn::GpuMem,
#[cfg(feature = "gpu")]
ProcColumn::GpuPercent => ProcWidgetColumn::GpuUtil,
}
}
}
#[cfg(test)] #[cfg(test)]
mod test { mod test {
use super::{ProcColumn, ProcessesConfig}; use super::{ProcColumn, ProcessesConfig};

View file

@ -1,5 +1,5 @@
pub mod proc_widget_column; pub mod process_columns;
pub mod proc_widget_data; pub mod process_data;
pub mod query; pub mod query;
mod sort_table; mod sort_table;
@ -8,8 +8,8 @@ use std::{borrow::Cow, collections::BTreeMap};
use hashbrown::{HashMap, HashSet}; use hashbrown::{HashMap, HashSet};
use indexmap::IndexSet; use indexmap::IndexSet;
use itertools::Itertools; use itertools::Itertools;
pub use proc_widget_column::*; pub use process_columns::*;
pub use proc_widget_data::*; pub use process_data::*;
use query::{parse_query, ProcessQuery}; use query::{parse_query, ProcessQuery};
use sort_table::SortTableColumn; use sort_table::SortTableColumn;
@ -76,8 +76,8 @@ fn make_column(column: ProcColumn) -> SortColumn<ProcColumn> {
match column { match column {
CpuPercent => SortColumn::new(CpuPercent).default_descending(), CpuPercent => SortColumn::new(CpuPercent).default_descending(),
MemoryValue => SortColumn::new(MemoryValue).default_descending(), MemValue => SortColumn::new(MemValue).default_descending(),
MemoryPercent => SortColumn::new(MemoryPercent).default_descending(), MemPercent => SortColumn::new(MemPercent).default_descending(),
Pid => SortColumn::new(Pid), Pid => SortColumn::new(Pid),
Count => SortColumn::new(Count), Count => SortColumn::new(Count),
Name => SortColumn::soft(Name, Some(0.3)), Name => SortColumn::soft(Name, Some(0.3)),
@ -90,9 +90,9 @@ fn make_column(column: ProcColumn) -> SortColumn<ProcColumn> {
State => SortColumn::hard(State, 9), State => SortColumn::hard(State, 9),
Time => SortColumn::new(Time), Time => SortColumn::new(Time),
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuMemoryValue => SortColumn::new(GpuMemoryValue).default_descending(), GpuMemValue => SortColumn::new(GpuMemValue).default_descending(),
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuMemoryPercent => SortColumn::new(GpuMemoryPercent).default_descending(), GpuMemPercent => SortColumn::new(GpuMemPercent).default_descending(),
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuUtilPercent => SortColumn::new(GpuUtilPercent).default_descending(), GpuUtilPercent => SortColumn::new(GpuUtilPercent).default_descending(),
} }
@ -248,9 +248,9 @@ impl ProcWidgetState {
ProcWidgetColumn::Cpu => CpuPercent, ProcWidgetColumn::Cpu => CpuPercent,
ProcWidgetColumn::Mem => { ProcWidgetColumn::Mem => {
if mem_as_values { if mem_as_values {
MemoryValue MemValue
} else { } else {
MemoryPercent MemPercent
} }
} }
ProcWidgetColumn::ReadPerSecond => ReadPerSecond, ProcWidgetColumn::ReadPerSecond => ReadPerSecond,
@ -263,9 +263,9 @@ impl ProcWidgetState {
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcWidgetColumn::GpuMem => { ProcWidgetColumn::GpuMem => {
if mem_as_values { if mem_as_values {
GpuMemoryValue GpuMemValue
} else { } else {
GpuMemoryPercent GpuMemPercent
} }
} }
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
@ -280,11 +280,7 @@ impl ProcWidgetState {
if is_count { Count } else { Pid }, if is_count { Count } else { Pid },
if is_command { Command } else { Name }, if is_command { Command } else { Name },
CpuPercent, CpuPercent,
if mem_as_values { if mem_as_values { MemValue } else { MemPercent },
MemoryValue
} else {
MemoryPercent
},
ReadPerSecond, ReadPerSecond,
WritePerSecond, WritePerSecond,
TotalRead, TotalRead,
@ -306,7 +302,7 @@ impl ProcWidgetState {
match col.inner() { match col.inner() {
CpuPercent => ProcWidgetColumn::Cpu, CpuPercent => ProcWidgetColumn::Cpu,
MemoryValue | MemoryPercent => ProcWidgetColumn::Mem, MemValue | MemPercent => ProcWidgetColumn::Mem,
Pid | Count => ProcWidgetColumn::PidOrCount, Pid | Count => ProcWidgetColumn::PidOrCount,
Name | Command => ProcWidgetColumn::ProcNameOrCommand, Name | Command => ProcWidgetColumn::ProcNameOrCommand,
ReadPerSecond => ProcWidgetColumn::ReadPerSecond, ReadPerSecond => ProcWidgetColumn::ReadPerSecond,
@ -317,7 +313,7 @@ impl ProcWidgetState {
User => ProcWidgetColumn::User, User => ProcWidgetColumn::User,
Time => ProcWidgetColumn::Time, Time => ProcWidgetColumn::Time,
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuMemoryValue | GpuMemoryPercent => ProcWidgetColumn::GpuMem, GpuMemValue | GpuMemPercent => ProcWidgetColumn::GpuMem,
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuUtilPercent => ProcWidgetColumn::GpuUtil, GpuUtilPercent => ProcWidgetColumn::GpuUtil,
} }
@ -382,7 +378,7 @@ impl ProcWidgetState {
self.column_mapping self.column_mapping
.get_index_of(&ProcWidgetColumn::Mem) .get_index_of(&ProcWidgetColumn::Mem)
.and_then(|index| self.table.columns.get(index)) .and_then(|index| self.table.columns.get(index))
.map(|col| matches!(col.inner(), ProcColumn::MemoryPercent)) .map(|col| matches!(col.inner(), ProcColumn::MemPercent))
.unwrap_or(false) .unwrap_or(false)
} }
@ -742,11 +738,11 @@ impl ProcWidgetState {
if let Some(index) = self.column_mapping.get_index_of(&ProcWidgetColumn::Mem) { if let Some(index) = self.column_mapping.get_index_of(&ProcWidgetColumn::Mem) {
if let Some(mem) = self.get_mut_proc_col(index) { if let Some(mem) = self.get_mut_proc_col(index) {
match mem { match mem {
ProcColumn::MemoryValue => { ProcColumn::MemValue => {
*mem = ProcColumn::MemoryPercent; *mem = ProcColumn::MemPercent;
} }
ProcColumn::MemoryPercent => { ProcColumn::MemPercent => {
*mem = ProcColumn::MemoryValue; *mem = ProcColumn::MemValue;
} }
_ => unreachable!(), _ => unreachable!(),
} }
@ -759,11 +755,11 @@ impl ProcWidgetState {
if let Some(index) = self.column_mapping.get_index_of(&ProcWidgetColumn::GpuMem) { if let Some(index) = self.column_mapping.get_index_of(&ProcWidgetColumn::GpuMem) {
if let Some(mem) = self.get_mut_proc_col(index) { if let Some(mem) = self.get_mut_proc_col(index) {
match mem { match mem {
ProcColumn::GpuMemoryValue => { ProcColumn::GpuMemValue => {
*mem = ProcColumn::GpuMemoryPercent; *mem = ProcColumn::GpuMemPercent;
} }
ProcColumn::GpuMemoryPercent => { ProcColumn::GpuMemPercent => {
*mem = ProcColumn::GpuMemoryValue; *mem = ProcColumn::GpuMemValue;
} }
_ => unreachable!(), _ => unreachable!(),
} }
@ -1110,7 +1106,7 @@ mod test {
); );
data.sort_by_key(|p| p.pid); data.sort_by_key(|p| p.pid);
sort_skip_pid_asc(&ProcColumn::MemoryPercent, &mut data, SortOrder::Descending); sort_skip_pid_asc(&ProcColumn::MemPercent, &mut data, SortOrder::Descending);
assert_eq!( assert_eq!(
[&b, &a, &c, &d].iter().map(|d| (d.pid)).collect::<Vec<_>>(), [&b, &a, &c, &d].iter().map(|d| (d.pid)).collect::<Vec<_>>(),
data.iter().map(|d| (d.pid)).collect::<Vec<_>>(), data.iter().map(|d| (d.pid)).collect::<Vec<_>>(),
@ -1118,7 +1114,7 @@ mod test {
// Note that the PID ordering for ties is still ascending. // Note that the PID ordering for ties is still ascending.
data.sort_by_key(|p| p.pid); data.sort_by_key(|p| p.pid);
sort_skip_pid_asc(&ProcColumn::MemoryPercent, &mut data, SortOrder::Ascending); sort_skip_pid_asc(&ProcColumn::MemPercent, &mut data, SortOrder::Ascending);
assert_eq!( assert_eq!(
[&c, &d, &a, &b].iter().map(|d| (d.pid)).collect::<Vec<_>>(), [&c, &d, &a, &b].iter().map(|d| (d.pid)).collect::<Vec<_>>(),
data.iter().map(|d| (d.pid)).collect::<Vec<_>>(), data.iter().map(|d| (d.pid)).collect::<Vec<_>>(),
@ -1168,7 +1164,7 @@ mod test {
let columns = vec![ let columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::Name, ProcColumn::Name,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::State, ProcColumn::State,
]; ];
let state = init_default_state(&init_columns); let state = init_default_state(&init_columns);
@ -1186,14 +1182,10 @@ mod test {
let original_columns = vec![ let original_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::Name, ProcColumn::Name,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::State, ProcColumn::State,
]; ];
let new_columns = vec![ let new_columns = vec![ProcColumn::Count, ProcColumn::Name, ProcColumn::MemPercent];
ProcColumn::Count,
ProcColumn::Name,
ProcColumn::MemoryPercent,
];
let mut state = init_default_state(&init_columns); let mut state = init_default_state(&init_columns);
assert_eq!(get_columns(&state.table), original_columns); assert_eq!(get_columns(&state.table), original_columns);
@ -1218,16 +1210,12 @@ mod test {
]; ];
let original_columns = vec![ let original_columns = vec![
ProcColumn::Name, ProcColumn::Name,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::User, ProcColumn::User,
ProcColumn::State, ProcColumn::State,
ProcColumn::Pid, ProcColumn::Pid,
]; ];
let new_columns = vec![ let new_columns = vec![ProcColumn::Name, ProcColumn::MemPercent, ProcColumn::Count];
ProcColumn::Name,
ProcColumn::MemoryPercent,
ProcColumn::Count,
];
let mut state = init_default_state(&init_columns); let mut state = init_default_state(&init_columns);
assert_eq!(get_columns(&state.table), original_columns); assert_eq!(get_columns(&state.table), original_columns);
@ -1252,13 +1240,13 @@ mod test {
let original_columns = vec![ let original_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::State, ProcColumn::State,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::Command, ProcColumn::Command,
]; ];
let new_columns = vec![ let new_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::State, ProcColumn::State,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::Name, ProcColumn::Name,
]; ];
@ -1286,13 +1274,13 @@ mod test {
]; ];
let original_columns = vec![ let original_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::State, ProcColumn::State,
ProcColumn::Name, ProcColumn::Name,
]; ];
let new_columns = vec![ let new_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::MemoryValue, ProcColumn::MemValue,
ProcColumn::State, ProcColumn::State,
ProcColumn::Name, ProcColumn::Name,
]; ];
@ -1317,13 +1305,13 @@ mod test {
]; ];
let original_columns = vec![ let original_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::MemoryValue, ProcColumn::MemValue,
ProcColumn::State, ProcColumn::State,
ProcColumn::Name, ProcColumn::Name,
]; ];
let new_columns = vec![ let new_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::State, ProcColumn::State,
ProcColumn::Name, ProcColumn::Name,
]; ];
@ -1352,7 +1340,7 @@ mod test {
]; ];
let original_columns = vec![ let original_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::State, ProcColumn::State,
ProcColumn::Command, ProcColumn::Command,
]; ];
@ -1382,7 +1370,7 @@ mod test {
]; ];
let original_columns = vec![ let original_columns = vec![
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::MemoryValue, ProcColumn::MemValue,
ProcColumn::State, ProcColumn::State,
ProcColumn::Name, ProcColumn::Name,
]; ];
@ -1417,13 +1405,13 @@ mod test {
ProcWidgetColumn::Mem, ProcWidgetColumn::Mem,
]; ];
let original_columns = vec![ let original_columns = vec![
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::State, ProcColumn::State,
ProcColumn::Name, ProcColumn::Name,
]; ];
let new_columns = vec![ let new_columns = vec![
ProcColumn::MemoryValue, ProcColumn::MemValue,
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::State, ProcColumn::State,
ProcColumn::Name, ProcColumn::Name,
@ -1456,14 +1444,10 @@ mod test {
let original_columns = vec![ let original_columns = vec![
ProcColumn::Name, ProcColumn::Name,
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
ProcColumn::State, ProcColumn::State,
]; ];
let new_columns = vec![ let new_columns = vec![ProcColumn::Name, ProcColumn::Count, ProcColumn::MemPercent];
ProcColumn::Name,
ProcColumn::Count,
ProcColumn::MemoryPercent,
];
let mut state = init_default_state(&init_columns); let mut state = init_default_state(&init_columns);
assert_eq!(get_columns(&state.table), original_columns); assert_eq!(get_columns(&state.table), original_columns);
@ -1495,13 +1479,13 @@ mod test {
ProcColumn::Command, ProcColumn::Command,
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::State, ProcColumn::State,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
]; ];
let new_columns = vec![ let new_columns = vec![
ProcColumn::Name, ProcColumn::Name,
ProcColumn::Pid, ProcColumn::Pid,
ProcColumn::State, ProcColumn::State,
ProcColumn::MemoryPercent, ProcColumn::MemPercent,
]; ];
let table_config = ProcTableConfig { let table_config = ProcTableConfig {

View file

@ -1,16 +1,22 @@
use std::{borrow::Cow, cmp::Reverse}; use std::{borrow::Cow, cmp::Reverse};
use super::ProcWidgetData; use serde::Deserialize;
use super::{ProcWidgetColumn, ProcWidgetData};
use crate::{ use crate::{
canvas::components::data_table::{ColumnHeader, SortsRow}, canvas::components::data_table::{ColumnHeader, SortsRow},
utils::general::sort_partial_fn, utils::general::sort_partial_fn,
}; };
#[derive(Debug, PartialEq, Eq, Copy, Clone, Hash)] #[derive(Debug, PartialEq, Eq, Copy, Clone, Hash)]
#[cfg_attr(
feature = "generate_schema",
derive(schemars::JsonSchema, strum::VariantArray)
)]
pub enum ProcColumn { pub enum ProcColumn {
CpuPercent, CpuPercent,
MemoryValue, MemValue,
MemoryPercent, MemPercent,
Pid, Pid,
Count, Count,
Name, Name,
@ -23,19 +29,47 @@ pub enum ProcColumn {
User, User,
Time, Time,
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuMemoryValue, GpuMemValue,
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuMemoryPercent, GpuMemPercent,
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
GpuUtilPercent, GpuUtilPercent,
} }
impl ProcColumn {
/// An ugly hack to generate the JSON schema.
#[cfg(feature = "generate_schema")]
pub fn get_schema_names(&self) -> &[&'static str] {
match self {
ProcColumn::Pid => &["PID"],
ProcColumn::Count => &["Count"],
ProcColumn::Name => &["Name"],
ProcColumn::Command => &["Command"],
ProcColumn::CpuPercent => &["CPU%"],
// TODO: Change this
ProcColumn::MemValue | ProcColumn::MemPercent => &["Mem", "Mem%"],
ProcColumn::ReadPerSecond => &["R/s", "Read", "Rps"],
ProcColumn::WritePerSecond => &["W/s", "Write", "Wps"],
ProcColumn::TotalRead => &["T.Read", "TWrite"],
ProcColumn::TotalWrite => &["T.Write", "TRead"],
ProcColumn::State => &["State"],
ProcColumn::User => &["User"],
ProcColumn::Time => &["Time"],
#[cfg(feature = "gpu")]
// TODO: Change this
ProcColumn::GpuMemValue | ProcColumn::GpuMemPercent => &["GMem", "GMem%"],
#[cfg(feature = "gpu")]
ProcColumn::GpuUtilPercent => &["GPU%"],
}
}
}
impl ColumnHeader for ProcColumn { impl ColumnHeader for ProcColumn {
fn text(&self) -> Cow<'static, str> { fn text(&self) -> Cow<'static, str> {
match self { match self {
ProcColumn::CpuPercent => "CPU%", ProcColumn::CpuPercent => "CPU%",
ProcColumn::MemoryValue => "Mem", ProcColumn::MemValue => "Mem",
ProcColumn::MemoryPercent => "Mem%", ProcColumn::MemPercent => "Mem%",
ProcColumn::Pid => "PID", ProcColumn::Pid => "PID",
ProcColumn::Count => "Count", ProcColumn::Count => "Count",
ProcColumn::Name => "Name", ProcColumn::Name => "Name",
@ -48,9 +82,9 @@ impl ColumnHeader for ProcColumn {
ProcColumn::User => "User", ProcColumn::User => "User",
ProcColumn::Time => "Time", ProcColumn::Time => "Time",
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuMemoryValue => "GMem", ProcColumn::GpuMemValue => "GMem",
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuMemoryPercent => "GMem%", ProcColumn::GpuMemPercent => "GMem%",
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuUtilPercent => "GPU%", ProcColumn::GpuUtilPercent => "GPU%",
} }
@ -60,8 +94,8 @@ impl ColumnHeader for ProcColumn {
fn header(&self) -> Cow<'static, str> { fn header(&self) -> Cow<'static, str> {
match self { match self {
ProcColumn::CpuPercent => "CPU%(c)", ProcColumn::CpuPercent => "CPU%(c)",
ProcColumn::MemoryValue => "Mem(m)", ProcColumn::MemValue => "Mem(m)",
ProcColumn::MemoryPercent => "Mem%(m)", ProcColumn::MemPercent => "Mem%(m)",
ProcColumn::Pid => "PID(p)", ProcColumn::Pid => "PID(p)",
ProcColumn::Count => "Count", ProcColumn::Count => "Count",
ProcColumn::Name => "Name(n)", ProcColumn::Name => "Name(n)",
@ -74,9 +108,9 @@ impl ColumnHeader for ProcColumn {
ProcColumn::User => "User", ProcColumn::User => "User",
ProcColumn::Time => "Time", ProcColumn::Time => "Time",
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuMemoryValue => "GMem", ProcColumn::GpuMemValue => "GMem",
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuMemoryPercent => "GMem%", ProcColumn::GpuMemPercent => "GMem%",
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuUtilPercent => "GPU%", ProcColumn::GpuUtilPercent => "GPU%",
} }
@ -94,7 +128,7 @@ impl SortsRow for ProcColumn {
sort_partial_fn(descending)(a.cpu_usage_percent, b.cpu_usage_percent) sort_partial_fn(descending)(a.cpu_usage_percent, b.cpu_usage_percent)
}); });
} }
ProcColumn::MemoryValue | ProcColumn::MemoryPercent => { ProcColumn::MemValue | ProcColumn::MemPercent => {
data.sort_by(|a, b| sort_partial_fn(descending)(&a.mem_usage, &b.mem_usage)); data.sort_by(|a, b| sort_partial_fn(descending)(&a.mem_usage, &b.mem_usage));
} }
ProcColumn::Pid => { ProcColumn::Pid => {
@ -140,7 +174,7 @@ impl SortsRow for ProcColumn {
data.sort_by(|a, b| sort_partial_fn(descending)(a.time, b.time)); data.sort_by(|a, b| sort_partial_fn(descending)(a.time, b.time));
} }
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuMemoryValue | ProcColumn::GpuMemoryPercent => { ProcColumn::GpuMemValue | ProcColumn::GpuMemPercent => {
data.sort_by(|a, b| { data.sort_by(|a, b| {
sort_partial_fn(descending)(&a.gpu_mem_usage, &b.gpu_mem_usage) sort_partial_fn(descending)(&a.gpu_mem_usage, &b.gpu_mem_usage)
}); });
@ -152,3 +186,56 @@ impl SortsRow for ProcColumn {
} }
} }
} }
impl<'de> Deserialize<'de> for ProcColumn {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: serde::Deserializer<'de>,
{
let value = String::deserialize(deserializer)?.to_lowercase();
match value.as_str() {
"cpu%" => Ok(ProcColumn::CpuPercent),
// TODO: Maybe change this in the future.
"mem" | "mem%" => Ok(ProcColumn::MemPercent),
"pid" => Ok(ProcColumn::Pid),
"count" => Ok(ProcColumn::Count),
"name" => Ok(ProcColumn::Name),
"command" => Ok(ProcColumn::Command),
"read" | "r/s" | "rps" => Ok(ProcColumn::ReadPerSecond),
"write" | "w/s" | "wps" => Ok(ProcColumn::WritePerSecond),
"tread" | "t.read" => Ok(ProcColumn::TotalRead),
"twrite" | "t.write" => Ok(ProcColumn::TotalWrite),
"state" => Ok(ProcColumn::State),
"user" => Ok(ProcColumn::User),
"time" => Ok(ProcColumn::Time),
#[cfg(feature = "gpu")]
// TODO: Maybe change this in the future.
"gmem" | "gmem%" => Ok(ProcColumn::GpuMemPercent),
#[cfg(feature = "gpu")]
"gpu%" => Ok(ProcColumn::GpuUtilPercent),
_ => Err(serde::de::Error::custom("doesn't match any column type")),
}
}
}
impl From<&ProcColumn> for ProcWidgetColumn {
fn from(value: &ProcColumn) -> Self {
match value {
ProcColumn::Pid | ProcColumn::Count => ProcWidgetColumn::PidOrCount,
ProcColumn::Name | ProcColumn::Command => ProcWidgetColumn::ProcNameOrCommand,
ProcColumn::CpuPercent => ProcWidgetColumn::Cpu,
ProcColumn::MemPercent | ProcColumn::MemValue => ProcWidgetColumn::Mem,
ProcColumn::ReadPerSecond => ProcWidgetColumn::ReadPerSecond,
ProcColumn::WritePerSecond => ProcWidgetColumn::WritePerSecond,
ProcColumn::TotalRead => ProcWidgetColumn::TotalRead,
ProcColumn::TotalWrite => ProcWidgetColumn::TotalWrite,
ProcColumn::State => ProcWidgetColumn::State,
ProcColumn::User => ProcWidgetColumn::User,
ProcColumn::Time => ProcWidgetColumn::Time,
#[cfg(feature = "gpu")]
ProcColumn::GpuMemPercent | ProcColumn::GpuMemValue => ProcWidgetColumn::GpuMem,
#[cfg(feature = "gpu")]
ProcColumn::GpuUtilPercent => ProcWidgetColumn::GpuUtil,
}
}
}

View file

@ -9,7 +9,7 @@ use std::{
use concat_string::concat_string; use concat_string::concat_string;
use tui::widgets::Row; use tui::widgets::Row;
use super::proc_widget_column::ProcColumn; use super::process_columns::ProcColumn;
use crate::{ use crate::{
canvas::{ canvas::{
components::data_table::{DataTableColumn, DataToCell}, components::data_table::{DataTableColumn, DataToCell},
@ -280,7 +280,7 @@ impl ProcWidgetData {
fn to_string(&self, column: &ProcColumn) -> String { fn to_string(&self, column: &ProcColumn) -> String {
match column { match column {
ProcColumn::CpuPercent => format!("{:.1}%", self.cpu_usage_percent), ProcColumn::CpuPercent => format!("{:.1}%", self.cpu_usage_percent),
ProcColumn::MemoryValue | ProcColumn::MemoryPercent => self.mem_usage.to_string(), ProcColumn::MemValue | ProcColumn::MemPercent => self.mem_usage.to_string(),
ProcColumn::Pid => self.pid.to_string(), ProcColumn::Pid => self.pid.to_string(),
ProcColumn::Count => self.num_similar.to_string(), ProcColumn::Count => self.num_similar.to_string(),
ProcColumn::Name | ProcColumn::Command => self.id.to_prefixed_string(), ProcColumn::Name | ProcColumn::Command => self.id.to_prefixed_string(),
@ -292,9 +292,7 @@ impl ProcWidgetData {
ProcColumn::User => self.user.clone(), ProcColumn::User => self.user.clone(),
ProcColumn::Time => format_time(self.time), ProcColumn::Time => format_time(self.time),
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuMemoryValue | ProcColumn::GpuMemoryPercent => { ProcColumn::GpuMemValue | ProcColumn::GpuMemPercent => self.gpu_mem_usage.to_string(),
self.gpu_mem_usage.to_string()
}
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuUtilPercent => format!("{:.1}%", self.gpu_usage), ProcColumn::GpuUtilPercent => format!("{:.1}%", self.gpu_usage),
} }
@ -312,9 +310,7 @@ impl DataToCell<ProcColumn> for ProcWidgetData {
// differences. // differences.
Some(match column { Some(match column {
ProcColumn::CpuPercent => format!("{:.1}%", self.cpu_usage_percent).into(), ProcColumn::CpuPercent => format!("{:.1}%", self.cpu_usage_percent).into(),
ProcColumn::MemoryValue | ProcColumn::MemoryPercent => { ProcColumn::MemValue | ProcColumn::MemPercent => self.mem_usage.to_string().into(),
self.mem_usage.to_string().into()
}
ProcColumn::Pid => self.pid.to_string().into(), ProcColumn::Pid => self.pid.to_string().into(),
ProcColumn::Count => self.num_similar.to_string().into(), ProcColumn::Count => self.num_similar.to_string().into(),
ProcColumn::Name | ProcColumn::Command => self.id.to_prefixed_string().into(), ProcColumn::Name | ProcColumn::Command => self.id.to_prefixed_string().into(),
@ -332,7 +328,7 @@ impl DataToCell<ProcColumn> for ProcWidgetData {
ProcColumn::User => self.user.clone().into(), ProcColumn::User => self.user.clone().into(),
ProcColumn::Time => format_time(self.time).into(), ProcColumn::Time => format_time(self.time).into(),
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
ProcColumn::GpuMemoryValue | ProcColumn::GpuMemoryPercent => { ProcColumn::GpuMemValue | ProcColumn::GpuMemPercent => {
self.gpu_mem_usage.to_string().into() self.gpu_mem_usage.to_string().into()
} }
#[cfg(feature = "gpu")] #[cfg(feature = "gpu")]
@ -369,7 +365,7 @@ impl DataToCell<ProcColumn> for ProcWidgetData {
mod test { mod test {
use std::time::Duration; use std::time::Duration;
use crate::widgets::proc_widget_data::format_time; use crate::widgets::process_data::format_time;
#[test] #[test]
fn test_format_time() { fn test_format_time() {