From 881e7399b2417c32fa996d94c6b389c1e06d8eb1 Mon Sep 17 00:00:00 2001 From: 魏曹先生 <1992414357@qq.com> Date: Tue, 28 Apr 2026 16:18:12 +0800 Subject: Add scaffolding CLI tool `mling` --- mling/src/cli/list.rs | 117 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 117 insertions(+) create mode 100644 mling/src/cli/list.rs (limited to 'mling/src/cli/list.rs') diff --git a/mling/src/cli/list.rs b/mling/src/cli/list.rs new file mode 100644 index 0000000..9aff22b --- /dev/null +++ b/mling/src/cli/list.rs @@ -0,0 +1,117 @@ +use colored::Colorize; +use mingling::{ + Groupped, RenderResult, ShellContext, Suggest, + macros::{chain, completion, dispatcher, pack, r_println, renderer, suggest}, + parser::Picker, +}; +use serde::Serialize; + +use crate::{ThisProgram, namespace_manager::list_namespaces}; + +dispatcher!("ls-namespace", ListInstalledCommand => ListInstalledEntry); + +#[completion(ListInstalledEntry)] +pub(crate) fn comp_list_installed(ctx: &ShellContext) -> Suggest { + if ctx.typing_argument() { + return suggest! { + "--trusted": "Show only trusted namespaces", + "--untrusted": "Show only untrusted namespaces", + }; + } + return suggest!(); +} + +#[derive(Debug, Serialize, Default, Groupped)] +pub(crate) enum StateListInstalledOptions { + #[default] + All, + OnlyTrusted, + OnlyUntrusted, +} + +pack!(MutexErrorListInstalled = ()); + +#[chain] +pub(crate) fn handle_list_installed_entry(prev: ListInstalledEntry) -> NextProcess { + let picker = Picker::new(prev.inner); + let r = picker + .pick::("--trusted") + .pick::("--untrusted") + .unpack(); + + let option: StateListInstalledOptions = match r { + // (show_trusted, show_untrusted) + (true, false) => StateListInstalledOptions::OnlyTrusted, + (false, true) => StateListInstalledOptions::OnlyUntrusted, + (false, false) => StateListInstalledOptions::All, + (true, true) => return MutexErrorListInstalled::default().to_render(), + }; + + option.to_chain() +} + +#[renderer] +pub(crate) fn render_list_installed_mutex_error(_prev: MutexErrorListInstalled) { + r_println!("Error: cannot use both --trusted and --untrusted options at the same time") +} + +#[derive(Debug, Groupped, Serialize)] +pub(crate) struct ResultInstalledNamespaces { + trusted: Vec, + untrusted: Vec, + untagged: Vec, + option: StateListInstalledOptions, +} + +#[chain] +pub(crate) fn handle_state_list_installed_option(prev: StateListInstalledOptions) -> NextProcess { + ResultInstalledNamespaces { + trusted: list_namespaces(true, false, false), + untrusted: list_namespaces(false, true, false), + untagged: list_namespaces(false, false, true), + option: prev, + } +} + +#[renderer] +pub(crate) fn render_installed(prev: ResultInstalledNamespaces) { + match prev.option { + StateListInstalledOptions::All => { + print_list("Trusted".bright_green().bold().to_string(), prev.trusted, r); + print_list( + "Unrusted".bright_red().bold().to_string(), + prev.untrusted, + r, + ); + print_list( + "Untagged".bright_black().bold().to_string(), + prev.untagged, + r, + ); + } + StateListInstalledOptions::OnlyTrusted => { + print_list("Trusted".bright_green().bold().to_string(), prev.trusted, r); + } + StateListInstalledOptions::OnlyUntrusted => { + print_list( + "Unrusted".bright_red().bold().to_string(), + prev.untrusted, + r, + ); + } + } +} + +fn print_list(title: String, list: Vec, r: &mut RenderResult) { + if list.is_empty() { + return; + } + + r_println!("{}", title); + + let mut i = 1; + for namespace in list.iter() { + r_println!(" {}. {}\n", i.to_string(), namespace.bold()); + i += 1; + } +} -- cgit