From 3790640524534aedddc77b54e30e8854636855a1 Mon Sep 17 00:00:00 2001 From: Michal S Date: Mon, 5 Sep 2022 17:09:27 +0100 Subject: [PATCH] [WIP] Potentially controversial arg change to support proper flag subcommands --- src/args.rs | 64 +++++++++-------------- src/internal/utils.rs | 5 +- src/main.rs | 116 +++++++++++++++++++++--------------------- 3 files changed, 85 insertions(+), 100 deletions(-) diff --git a/src/args.rs b/src/args.rs index 7bb700b..d4cac76 100644 --- a/src/args.rs +++ b/src/args.rs @@ -4,7 +4,7 @@ use crate::operations::SearchBy; use clap::{Parser, Subcommand, ValueHint}; #[derive(Debug, Clone, Parser)] -#[clap(bin_name = "ame", name = "Amethyst", version = env ! ("CARGO_PKG_VERSION"), about = env ! ("CARGO_PKG_DESCRIPTION"), infer_subcommands = true, allow_external_subcommands = true, allow_hyphen_values = true)] +#[clap(bin_name = "ame", name = "Amethyst", version = env ! ("CARGO_PKG_VERSION"), about = env ! ("CARGO_PKG_DESCRIPTION"), infer_subcommands = true)] pub struct Args { #[clap(subcommand)] pub subcommand: Option, @@ -28,40 +28,36 @@ pub struct Args { #[derive(Debug, Clone, Subcommand)] pub enum Operation { - /// Installs a package from either the AUR or the Pacman-defined repositories - #[clap(bin_name = "ame", name = "install", visible_aliases = & ["-S", "i"], aliases = & ["-Sa", "-Sr"])] + /// Installs or searches for a package in either the AUR or the Pacman-defined repositories + #[clap(bin_name = "ame", name = "sync", aliases = & [ "-S" ], visible_aliases = & ["install", "i"], short_flag = 'S')] Install(InstallArgs), /// Removes a previously installed package - #[clap(bin_name = "ame", name = "remove", visible_aliases = & ["rm", "r", "-Rs"])] + #[clap(bin_name = "ame", name = "remove", visible_aliases = & ["rm", "r"], short_flag = 'R')] Remove(RemoveArgs), - /// Searches for packages matching a provided pattern in the AUR/repos - #[clap(bin_name = "ame", name = "search", visible_aliases = & ["-Ss", "s"], aliases = & ["-Ssa", "-Ssr"])] - Search(SearchArgs), + /// Searches for packages matching a provided pattern in the AUR/repos [aliases: -Ss] + #[clap(bin_name = "ame", name = "search")] + Search(InstallArgs), /// Queries installed packages - #[clap(bin_name = "ame", name = "query", visible_aliases = & ["-Q", "q"], aliases = & ["-Qa", "-Qr", "-Qm", "-Qn"])] + #[clap(bin_name = "ame", name = "query", visible_aliases = & ["q"], short_flag = 'Q')] Query(QueryArgs), - /// Gets info about a package - #[clap(bin_name = "ame", name = "info", visible_aliases = & ["-Qi"])] - Info(InfoArgs), - /// Upgrades locally installed packages to their latest versions (Default) - #[clap(bin_name = "ame", name = "upgrade", visible_aliases = & ["-Syu", "u"])] + #[clap(bin_name = "ame", name = "upgrade", visible_aliases = & ["u", "-Syu"])] Upgrade(UpgradeArgs), /// Generates shell completions for supported shells (bash, fish, elvish, pwsh) - #[clap(bin_name = "ame", name = "gencomp", visible_aliases = & ["-g"])] + #[clap(bin_name = "ame", name = "gencomp", visible_aliases = & ["g"], short_flag = 'G')] GenComp(GenCompArgs), /// Removes all orphaned packages - #[clap(bin_name = "ame", name = "clean", visible_aliases = & ["-Sc", "c"])] + #[clap(bin_name = "ame", name = "clean", visible_aliases = & ["c"], short_flag = 'C')] Clean, /// Runs pacdiff - #[clap(bin_name = "ame", name = "diff", visible_aliases = & ["-d"])] + #[clap(bin_name = "ame", name = "diff", visible_aliases = & ["d"], short_flag = 'd')] Diff, } @@ -84,6 +80,14 @@ pub struct InstallArgs { /// Install the packages only from the pacman-defined repositories [-Sr] #[clap(long, short)] pub repo: bool, + + /// Search packages for a given pattern instead of installing + #[clap(hidden = true, short = 's')] + pub search: bool, + + /// Searches by a specific field + #[clap(long, short)] + pub by: Option, } #[derive(Default, Debug, Clone, Parser)] @@ -93,25 +97,6 @@ pub struct RemoveArgs { pub packages: Vec, } -#[derive(Default, Debug, Clone, Parser)] -pub struct SearchArgs { - /// Searches for the relevant packages in the AUR [-Ssa] - #[clap(long, short)] - pub aur: bool, - - /// Searches only pacman repos for the package [-Ssr] - #[clap(long, short)] - pub repo: bool, - - /// The string the package must match in the search - #[clap(required = true)] - pub search: String, - - /// Searches by a specific field - #[clap(long, short)] - pub by: Option, -} - #[derive(Default, Debug, Clone, Parser)] pub struct QueryArgs { /// Lists AUR/foreign packages [-Qa, -Qm] @@ -121,13 +106,10 @@ pub struct QueryArgs { /// Lists repo/native packages [-Qr, -Qn] #[clap(long, short)] pub repo: bool, -} -#[derive(Default, Debug, Clone, Parser)] -pub struct InfoArgs { - /// The name of the package(s) to get info on - #[clap(required = true)] - pub package: String, + /// Get information about a specific package + #[clap(long, short)] + pub info: Option, } #[derive(Default, Debug, Clone, Parser)] diff --git a/src/internal/utils.rs b/src/internal/utils.rs index 4ed631a..5263758 100644 --- a/src/internal/utils.rs +++ b/src/internal/utils.rs @@ -65,8 +65,9 @@ fn create_if_not_exist(dir: &Path) -> &Path { pub fn wrap_text>(s: S, padding: usize) -> Vec { let subsequent_padding = " ".repeat(padding); - let opts = textwrap::Options::new(crossterm::terminal::size().unwrap().0 as usize - padding) - .subsequent_indent(&subsequent_padding); + let opts = + textwrap::Options::new(crossterm::terminal::size().unwrap().0 as usize - (padding + 1)) + .subsequent_indent(&subsequent_padding); wrap(s.as_ref(), opts) .into_iter() .map(String::from) diff --git a/src/main.rs b/src/main.rs index 866fe26..782a3b3 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,11 +1,11 @@ -use args::{Args, GenCompArgs, InfoArgs}; +use args::{Args, GenCompArgs}; use builder::pacman::{PacmanColor, PacmanQueryBuilder}; use clap::Parser; use internal::commands::ShellCommand; use internal::error::SilentUnwrap; -use crate::args::{InstallArgs, Operation, QueryArgs, RemoveArgs, SearchArgs}; +use crate::args::{InstallArgs, Operation, QueryArgs, RemoveArgs}; use crate::interact::page_string; use crate::internal::detect; use crate::internal::exit_code::AppExitCode; @@ -14,7 +14,6 @@ use crate::logging::get_logger; use crate::logging::Printable; use clap_complete::{Generator, Shell}; -use std::env; use std::str::FromStr; mod args; @@ -49,7 +48,14 @@ async fn main() { match args.subcommand.unwrap_or_default() { Operation::Install(install_args) => cmd_install(install_args, options).await, Operation::Remove(remove_args) => cmd_remove(remove_args, options).await, - Operation::Search(search_args) => cmd_search(search_args, options).await, + Operation::Search(search_args) => { + let args = InstallArgs { + search: true, + ..search_args + }; + + cmd_install(args, options).await; + } Operation::Query(query_args) => cmd_query(query_args).await, Operation::Upgrade(upgrade_args) => { tracing::info!("Performing system upgrade"); @@ -59,7 +65,6 @@ async fn main() { tracing::info!("Removing orphaned packages"); operations::clean(options).await; } - Operation::Info(info_args) => cmd_info(info_args).await, Operation::GenComp(gen_args) => cmd_gencomp(&gen_args), Operation::Diff => todo!(), } @@ -69,37 +74,40 @@ async fn main() { #[tracing::instrument(level = "trace")] async fn cmd_install(args: InstallArgs, options: Options) { - let packages = args.packages; - - let arg1 = env::args().collect::>()[1].clone(); - let both = !args.aur && arg1 != "-Sa" && arg1 != "-Sr"; - let aur = args.aur || arg1 == "-Sa"; - let repo = args.repo || arg1 == "-Sr"; - - if repo { - operations::install(packages, options).await; - return; - } - - if aur { - operations::aur_install(packages, options).await; - return; - } + let packages = &args.packages; + let both = !args.aur && !args.repo; - if both { - let sorted = sort(&packages, options).await; - if !sorted.nf.is_empty() { - crash!( - AppExitCode::PacmanError, - "Couldn't find packages: {} in repos or the AUR", - sorted.nf.join(", ") - ); - } - if !sorted.repo.is_empty() { - operations::install(sorted.repo, options).await; + match args.search { + true => { + cmd_search(args, options).await; } - if !sorted.aur.is_empty() { - operations::aur_install(sorted.aur, options).await; + false => { + if args.repo && !args.aur { + operations::install(packages.to_vec(), options).await; + return; + } + + if args.aur && !args.repo { + operations::aur_install(packages.to_vec(), options).await; + return; + } + + if both { + let sorted = sort(packages, options).await; + if !sorted.nf.is_empty() { + crash!( + AppExitCode::PacmanError, + "Couldn't find packages: {} in repos or the AUR", + sorted.nf.join(", ") + ); + } + if !sorted.repo.is_empty() { + operations::install(sorted.repo, options).await; + } + if !sorted.aur.is_empty() { + operations::aur_install(sorted.aur, options).await; + } + } } }; } @@ -112,22 +120,18 @@ async fn cmd_remove(args: RemoveArgs, options: Options) { } #[tracing::instrument(level = "trace")] -async fn cmd_search(args: SearchArgs, options: Options) { - let query_string = args.search; +async fn cmd_search(args: InstallArgs, options: Options) { + let query_string = args.packages.join(" "); + let both = !args.aur && !args.repo; let mut results = Vec::new(); - let arg1 = env::args().collect::>()[1].clone(); - let both = !args.aur && arg1 != "-Ssa" && arg1 != "-Ssr"; - let aur = args.aur || arg1 == "-Ssa" || both; - let repo = args.repo || arg1 == "-Ssr" || both; - - if repo { + if args.repo || both { tracing::info!("Searching repos for {}", &query_string); let res = operations::search(&query_string, options).await; results.extend(res); } - if aur { + if args.aur || both { tracing::info!("Searching AUR for {}", &query_string); let res = operations::aur_search(&query_string, args.by, options).await; results.extend(res); @@ -158,12 +162,9 @@ async fn cmd_search(args: SearchArgs, options: Options) { #[tracing::instrument(level = "trace")] async fn cmd_query(args: QueryArgs) { - let arg1 = env::args().collect::>()[1].clone(); - let both = !args.aur && arg1 != "-Qa" && arg1 != "-Qr"; - let aur = args.aur || arg1 == "-Qa" || both; - let repo = args.repo || arg1 == "-Qr" || both; + let both = !args.aur && !args.repo && args.info.is_none(); - if repo { + if args.repo { tracing::info!("Installed Repo Packages: "); PacmanQueryBuilder::native() .color(PacmanColor::Always) @@ -171,7 +172,8 @@ async fn cmd_query(args: QueryArgs) { .await .silent_unwrap(AppExitCode::PacmanError); } - if aur { + + if args.aur { tracing::info!("Installed AUR Packages: "); PacmanQueryBuilder::foreign() .color(PacmanColor::Always) @@ -179,6 +181,7 @@ async fn cmd_query(args: QueryArgs) { .await .silent_unwrap(AppExitCode::PacmanError); } + if both { tracing::info!("Installed Packages: "); PacmanQueryBuilder::all() @@ -187,15 +190,14 @@ async fn cmd_query(args: QueryArgs) { .await .silent_unwrap(AppExitCode::PacmanError); } -} -#[tracing::instrument(level = "trace")] -async fn cmd_info(args: InfoArgs) { - PacmanQueryBuilder::info() - .package(args.package) - .query() - .await - .silent_unwrap(AppExitCode::PacmanError); + if let Some(info) = args.info { + PacmanQueryBuilder::info() + .package(info) + .query() + .await + .silent_unwrap(AppExitCode::PacmanError); + } } #[tracing::instrument(level = "trace")]