diff options
Diffstat (limited to 'vendor/clap/examples/git-derive.rs')
-rw-r--r-- | vendor/clap/examples/git-derive.rs | 165 |
1 files changed, 165 insertions, 0 deletions
diff --git a/vendor/clap/examples/git-derive.rs b/vendor/clap/examples/git-derive.rs new file mode 100644 index 0000000..9d17137 --- /dev/null +++ b/vendor/clap/examples/git-derive.rs @@ -0,0 +1,165 @@ +use std::ffi::OsStr; +use std::ffi::OsString; +use std::path::PathBuf; + +use clap::{Args, Parser, Subcommand, ValueEnum}; + +/// A fictional versioning CLI +#[derive(Debug, Parser)] // requires `derive` feature +#[command(name = "git")] +#[command(about = "A fictional versioning CLI", long_about = None)] +struct Cli { + #[command(subcommand)] + command: Commands, +} + +#[derive(Debug, Subcommand)] +enum Commands { + /// Clones repos + #[command(arg_required_else_help = true)] + Clone { + /// The remote to clone + remote: String, + }, + /// Compare two commits + Diff { + #[arg(value_name = "COMMIT")] + base: Option<OsString>, + #[arg(value_name = "COMMIT")] + head: Option<OsString>, + #[arg(last = true)] + path: Option<OsString>, + #[arg( + long, + require_equals = true, + value_name = "WHEN", + num_args = 0..=1, + default_value_t = ColorWhen::Auto, + default_missing_value = "always", + value_enum + )] + color: ColorWhen, + }, + /// pushes things + #[command(arg_required_else_help = true)] + Push { + /// The remote to target + remote: String, + }, + /// adds things + #[command(arg_required_else_help = true)] + Add { + /// Stuff to add + #[arg(required = true)] + path: Vec<PathBuf>, + }, + Stash(StashArgs), + #[command(external_subcommand)] + External(Vec<OsString>), +} + +#[derive(ValueEnum, Copy, Clone, Debug, PartialEq, Eq)] +enum ColorWhen { + Always, + Auto, + Never, +} + +impl std::fmt::Display for ColorWhen { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + self.to_possible_value() + .expect("no values are skipped") + .get_name() + .fmt(f) + } +} + +#[derive(Debug, Args)] +#[command(args_conflicts_with_subcommands = true)] +#[command(flatten_help = true)] +struct StashArgs { + #[command(subcommand)] + command: Option<StashCommands>, + + #[command(flatten)] + push: StashPushArgs, +} + +#[derive(Debug, Subcommand)] +enum StashCommands { + Push(StashPushArgs), + Pop { stash: Option<String> }, + Apply { stash: Option<String> }, +} + +#[derive(Debug, Args)] +struct StashPushArgs { + #[arg(short, long)] + message: Option<String>, +} + +fn main() { + let args = Cli::parse(); + + match args.command { + Commands::Clone { remote } => { + println!("Cloning {remote}"); + } + Commands::Diff { + mut base, + mut head, + mut path, + color, + } => { + if path.is_none() { + path = head; + head = None; + if path.is_none() { + path = base; + base = None; + } + } + let base = base + .as_deref() + .map(|s| s.to_str().unwrap()) + .unwrap_or("stage"); + let head = head + .as_deref() + .map(|s| s.to_str().unwrap()) + .unwrap_or("worktree"); + let path = path.as_deref().unwrap_or_else(|| OsStr::new("")); + println!( + "Diffing {}..{} {} (color={})", + base, + head, + path.to_string_lossy(), + color + ); + } + Commands::Push { remote } => { + println!("Pushing to {remote}"); + } + Commands::Add { path } => { + println!("Adding {path:?}"); + } + Commands::Stash(stash) => { + let stash_cmd = stash.command.unwrap_or(StashCommands::Push(stash.push)); + match stash_cmd { + StashCommands::Push(push) => { + println!("Pushing {push:?}"); + } + StashCommands::Pop { stash } => { + println!("Popping {stash:?}"); + } + StashCommands::Apply { stash } => { + println!("Applying {stash:?}"); + } + } + } + Commands::External(args) => { + println!("Calling out to {:?} with {:?}", &args[0], &args[1..]); + } + } + + // Continued program logic goes here... +} |