extern crate gumdrop;
#[macro_use] extern crate gumdrop_derive;
use std::env::args;
use gumdrop::Options;
#[derive(Debug, Default, Options)]
struct MyOptions {
#[options(help = "print help message")]
help: bool,
#[options(help = "be verbose")]
verbose: bool,
#[options(command)]
command: Option<Command>,
#[options(command_name)]
command_name: Option<String>,
}
#[derive(Debug, Options)]
enum Command {
#[options(help = "make stuff")]
Make(MakeOpts),
#[options(help = "install stuff")]
Install(InstallOpts),
}
#[derive(Debug, Default, Options)]
struct MakeOpts {
#[options(help = "print help message")]
help: bool,
#[options(free)]
free: Vec<String>,
#[options(help = "number of jobs", meta = "N")]
jobs: Option<u32>,
}
#[derive(Debug, Default, Options)]
struct InstallOpts {
#[options(help = "print help message")]
help: bool,
#[options(help = "target directory")]
dir: Option<String>,
}
fn main() {
let args: Vec<String> = args().collect();
let opts = match MyOptions::parse_args_default(&args[1..]) {
Ok(opts) => opts,
Err(e) => {
println!("{}: {}", args[0], e);
return;
}
};
if opts.help_requested() {
match opts.command_name {
None => {
println!("Usage: {} [OPTIONS] [COMMAND] [ARGUMENTS]", args[0]);
println!();
println!("{}", MyOptions::usage());
println!();
println!("Available commands:");
println!();
println!("{}", Command::usage());
}
Some(ref cmd) => {
if let Some(help) = Command::command_usage(cmd) {
if help.is_empty() {
println!("command `{}` has no options", cmd);
} else {
println!("command `{}` accepts the following options:", cmd);
println!();
println!("{}", help);
}
} else {
println!("{}: unrecognized command: {}", args[0], cmd);
}
}
}
} else {
println!("{:#?}", opts);
}
}