clap
Análise de argumentos baseada em derive com validação, geração de ajuda e subcomandos.
Receita
use clap::Parser;
#[derive(Parser)]
#[command(name = "greet", version, about = "Cumprimenta alguém")]
struct Args {
/// Nome para cumprimentar
name: String,
/// Número de vezes para cumprimentar
#[arg(short, long, default_value_t = 1)]
count: u8,
}
fn main() {
let args = Args::parse();
for _ in 0..args.count {
println!("Olá, {}!", args.name);
}
}Quando usar isso: Qualquer CLI com mais de uma ou duas flags. clap é o padrão de fato no ecossistema Rust.
Exemplo de Trabalho
use clap::{Parser, Subcommand, ValueEnum};
use std::path::PathBuf;
#[derive(Parser)]
#[command(name = "backup", version, about = "Faz backup de arquivos")]
struct Cli {
/// Aumenta a verbosidade (-v, -vv)
#[arg(short, long, action = clap::ArgAction::Count)]
verbose: u8,
/// Caminho do arquivo de configuração
#[arg(short, long, env = "BACKUP_CONFIG")]
config: Option<PathBuf>,
#[command(subcommand)]
command: Command,
}
#[derive(Subcommand)]
enum Command {
/// Cria um novo backup
Create {
#[arg(value_enum)]
format: Format,
source: PathBuf,
},
/// Lista backups existentes
List,
}
#[derive(Clone, ValueEnum)]
enum Format {
Tar,
Zip,
}
fn main() -> anyhow::Result<()> {
let cli = Cli::parse();
match cli.command {
Command::Create { format, source } => {
println!("fazendo backup de {source:?} como {format:?}");
}
Command::List => println!("ainda não há backups"),
}
Ok(())
}O que isso demonstra:
- Macros
derivegeram--helpe validação automaticamente env =vincula variáveis de ambiente a flagsValueEnumrestringe escolhas a um conjunto tipado- Subcomandos organizam CLIs multi-verbo
Mergulho Profundo
Como Funciona
#[derive(Parser)]expande para uma implementaçãoparse()em tempo de compilação- Comentários de documentação em campos se tornam texto de ajuda
ArgAction::Countimplementa padrões de verbosidade-v/-vv- Erros imprimem dicas de uso e saem com o código 2
Atributos Comuns
| Atributo | Propósito |
|---|---|
short, long | Flags -n e --name |
default_value_t | Padrão quando a flag é omitida |
required = true | Falha se o argumento estiver faltando |
conflicts_with | Flags mutuamente exclusivas |
requires | Grupos de flags dependentes |
Alternativa da API Builder
Use a API builder quando precisar de argumentos dinâmicos em tempo de execução.
use clap::{Arg, Command};
let cmd = Command::new("dynamic")
.arg(Arg::new("file").required(true));
let matches = cmd.get_matches();Armadilhas
- Recurso
deriveausente - Adicioneclap = { version = "4", features = ["derive"] }. Correção: Habilite o recurso derive emCargo.toml. - Subcomandos de enum precisam de
Subcommandderive - Enums simples falham na compilação. Correção: Adicione#[derive(Subcommand)]. default_valuevsdefault_value_t- Padrões de string precisam de aspas; padrões tipados usam_t. Correção: Combine o atributo com o tipo do seu campo.- Estruturas aninhadas achatadas -
#[command(flatten)]mescla argumentos, mas pode causar colisões de nomes. Correção: Use nomes de campo únicos ouidexplícito. - Versão da ajuda desatualizada - Strings de versão codificadas ficam desatualizadas. Correção: Use
#[command(version = env!("CARGO_PKG_VERSION"))].
Alternativas
| Alternativa | Use Quando | Não Use Quando |
|---|---|---|
argh | Tamanho mínimo do binário, flags estilo Google | Você precisa de subcomandos ricos |
pico-args | Pegada de dependência minúscula | Regras de validação complexas |
std::env::args manual | Aprendizado ou scripts descartáveis | Ferramentas de produção com --help |
FAQs
clap 3 vs clap 4?
clap 4 é a API estável atual. Novos projetos devem usar clap 4 com macros derive.
Como exigir um subcomando?
Adicione #[command(subcommand_required = true)] na struct Parser raiz.
Posso analisar de um Vec em vez de argv?
Sim. Use Args::parse_from(["prog", "--flag", "value"]) em testes.
Como ocultar flags internas?
Use #[arg(hide = true)] no campo.
Flags globais entre subcomandos?
Coloque as flags na struct raiz. Elas se aplicam a todos os subcomandos automaticamente.
Como validar se um caminho existe?
Use value_parser = clap::value_parser!(PathBuf) mais um validador personalizado, ou verifique em main após a análise.
Compleções de shell?
Use o crate clap_complete. Veja a página de completações de shell.
Testando parsers clap?
Chame parse_from com argv sintético em testes unitários. Afirme sobre Err para entrada inválida.
Como mostrar padrões na ajuda?
Padrões aparecem automaticamente quando você define default_value ou default_value_t.
Texto de `about` multilinha?
Use #[command(about = "...")] ou long_about para descrições estendidas.
Relacionado
- Fundamentos de CLI - fundamentos
- Configuração e Ambiente - vinculação de variáveis de ambiente
- Completions de Shell e Páginas Man - completions
- Relatório de Erros - erros amigáveis ao usuário
Versões da Pilha: Esta página foi escrita para Rust 1.97.0 (edição 2024), Tokio 1.x, Axum 0.8, serde 1.0, sqlx 0.8, clap 4, e Polars 0.46+.