What it is
clap is Rust's command-line argument parser, generating parsing, validation, help text and shell completions from a derived struct.
Annotate a struct with #[derive(Parser)]; fields become flags and arguments. Subcommands are an enum. Doc comments become the help text.
Installation
cargo add clap --features deriveGetting started
The smallest useful thing you can do with it, and what each part means.
rust
use clap::Parser;
/// Manage a book library.
#[derive(Parser)]
#[command(version, about, long_about = None)]
struct Cli {
/// Path to the library file
#[arg(short, long, default_value = "library.json")]
file: PathBuf,
/// Increase output verbosity
#[arg(short, long, action = clap::ArgAction::Count)]
verbose: u8,
/// Titles to add
titles: Vec<String>,
}
let cli = Cli::parse(); // exits with help/errors automaticallyrust
#[derive(Parser)]
struct Cli {
#[command(subcommand)]
command: Command,
}
#[derive(clap::Subcommand)]
enum Command {
/// Add a book
Add { title: String, #[arg(long)] year: Option<u16> },
/// Remove a book
Remove { id: u32 },
}
match cli.command {
Command::Add { title, year } => add(title, year),
Command::Remove { id } => remove(id),
}Advanced usage
Where the library earns its place over a simpler alternative.
rust
#[derive(Parser)]
struct Cli {
#[arg(long, env = "API_TOKEN", hide_env_values = true)]
token: String,
#[arg(long, value_parser = clap::value_parser!(u16).range(1..=65535))]
port: u16,
#[arg(long, value_enum, default_value_t = Format::Json)]
format: Format,
}
// Generate a completion script at build time or behind a hidden flag.
clap_complete::generate(Shell::Zsh, &mut Cli::command(), "library", &mut io::stdout());Errors and fixes
The failures you are most likely to hit, and what actually resolves them.
- Compile error about ArgAction
- Version 3 and 4 differ substantially. Check which version the example targets — most older tutorials are for v3.
- Long compile times
- clap with derive is heavy. Disable default features and enable only what you need if binary size matters.
Best practices
- Use the derive API; the builder is only needed for arguments constructed at runtime.
- Write doc comments — they become the help text.
- Use value_parser for ranges and enums so invalid input is rejected before your code runs.
- Ship completions with the binary; it is a small change with a large usability payoff.
Background
Why it exists, and what it was reacting to.
clap's derive API turned argument parsing into a matter of describing a struct. Version 4 sharpened error messages and cut compile time and binary size considerably.
