a no-dependency command line parser for rust.
install miniclap via cargo:
cargo add miniclapinstall the latest unstable version of miniclap:
cargo add miniclap --git https://github.com/bedrock-pm/miniclap.gitdefine your app with a builder, then parse:
use miniclap::{App, Arg, ArgKind};
let app = App::new("tool")
.about("does something useful")
.arg(Arg::new("verbose", 'v', ArgKind::Count))
.arg(Arg::new("output", 'o', ArgKind::Value))
.arg(Arg::positional("file"));
let matches = app.parse_args(&["--output", "out.txt", "-vv", "input.txt"]);
println!("{}", matches.count("verbose")); // 2
println!("{}", matches.value("output").unwrap()); // "out.txt"
println!("{}", matches.positionals()[0]); // "input.txt"| kind | description | example |
|---|---|---|
Flag |
present or absent | --verbose |
Count |
how many times it appears | -vvv → 3 |
Value |
takes a string argument | --output file.txt or --output=file.txt |
Positional |
bare non-flag arguments | mytool foo.txt |
let app = App::new("tool")
.subcommand(
App::new("add")
.about("add a package")
.arg(Arg::positional("package"))
.arg(Arg::new("force", 'f', ArgKind::Flag))
);
let matches = app.parse_args(&["add", "--force", "serde"]);
let sub = matches.subcommand("add").unwrap();
println!("{}", sub.flag("force")); // true
println!("{}", sub.positionals()[0]); // "serde"subcommands can be nested arbitrarily deep. -h / --help at any level prints help scoped to that subcommand.
miniclap generates and prints help automatically — no setup needed. calling parse or parse_args will intercept -h / --help, print the help screen, and exit.
you can also print help manually:
// print help for the root app
app.print_help();
// print help for a subcommand, with the correct parent prefix in the usage line
app.find_subcommand("add").unwrap().print_help_with_parents(&["mytool"]);Tip
if your command module has a fallthrough arm that should show subcommand help, use
print_help_with_parents rather than print_help so the usage line reads
mytool add <COMMAND> instead of just add <COMMAND>.
use .no_short() to define a long-only flag:
Arg::new("dry-run", ' ', ArgKind::Flag).no_short()subcommands can be grouped under named categories in the help output:
App::new("sub").category("plumbing")subcommands without a category are grouped under other: if any categorised commands exist.
| method | description |
|---|---|
App::new(name) |
create a new app |
.about(text) |
set the description shown in help |
.category(label) |
set the category for help grouping |
.arg(arg) |
add an argument |
.subcommand(app) |
add a subcommand |
.args() |
iterate over registered args |
.find_subcommand(name) |
look up a subcommand by name |
.parse() |
parse std::env::args() |
.parse_args(argv) |
parse a given slice |
.print_help() |
print help and return |
.print_help_with_parents(parents) |
print help with a parent prefix |
| method | description |
|---|---|
.flag(name) |
true if the flag was passed |
.count(name) |
how many times the flag appeared |
.value(name) |
Some(&str) if a value was provided |
.positionals() |
slice of bare positional arguments |
.subcommand(name) |
Some(&Matches) for the matched subcommand |
.subcommand_name() |
name of the matched subcommand, if any |
i got tired of waiting for clap and it's many dependencies to install. so i made a no-dep clap alternative!