npx skills add https://github.com/bobmatnyc/claude-mpm-skills --skill clapClap 提供了声明式的命令行解析功能,具有强大的帮助输出、验证和子命令支持。使用它来构建具有可预测用户体验和可测试执行路径的命令行界面。
✅ 正确:派生 Parser
use clap::Parser;
#[derive(Parser, Debug)]
#[command(name = "mytool", version, about = "Example CLI")]
struct Args {
/// 启用详细输出
#[arg(long)]
verbose: bool,
/// 输入文件路径
#[arg(value_name = "FILE")]
input: String,
}
fn main() {
let args = Args::parse();
if args.verbose {
eprintln!("verbose enabled");
}
println!("input={}", args.input);
}
❌ 错误:多次解析
fn main() {
let _a = Args::parse();
let _b = Args::parse(); // 重复解析且行为不一致
}
使用子命令和共享的全局标志来建模多模式 CLI。
✅ 正确:全局标志 + 子命令
use clap::{Parser, Subcommand, ValueEnum};
#[derive(Parser, Debug)]
struct Args {
#[arg(long, global = true)]
verbose: bool,
#[arg(long, global = true, env = "MYTOOL_CONFIG")]
config: Option<String>,
#[command(subcommand)]
cmd: Command,
}
#[derive(Subcommand, Debug)]
enum Command {
Serve { #[arg(long, default_value_t = 3000)] port: u16 },
Migrate { #[arg(long, value_enum, default_value_t = Mode::Up)] mode: Mode },
}
#[derive(Copy, Clone, Debug, ValueEnum)]
enum Mode { Up, Down }
fn main() {
let args = Args::parse();
match args.cmd {
Command::Serve { port } => println!("serve on {}", port),
Command::Migrate { mode } => println!("migrate: {:?}", mode),
}
}
广告位招租
在这里展示您的产品或服务
触达数万 AI 开发者,精准高效
优先采用明确的优先级顺序:
✅ 正确:合并配置并允许 CLI 覆盖
use clap::Parser;
use serde::Deserialize;
#[derive(Parser, Debug)]
struct Args {
#[arg(long, env = "APP_PORT")]
port: Option<u16>,
}
#[derive(Deserialize)]
struct FileConfig {
port: Option<u16>,
}
fn effective_port(args: &Args, file: &FileConfig) -> u16 {
args.port.or(file.port).unwrap_or(3000)
}
将失败映射到稳定的退出码。从命令处理函数返回 Result 并集中处理打印。
✅ 正确:命令返回 Result
use std::process::ExitCode;
fn main() -> ExitCode {
match run() {
Ok(()) => ExitCode::SUCCESS,
Err(e) => {
eprintln!("{e}");
ExitCode::from(1)
}
}
}
fn run() -> Result<(), String> {
Ok(())
}
测试二进制程序的表面行为(参数、输出、退出码),而无需与内部实现耦合。
✅ 正确:集成测试
use assert_cmd::Command;
#[test]
fn shows_help() {
Command::cargo_bin("mytool")
.unwrap()
.arg("--help")
.assert()
.success();
}
为 Bash/Zsh/Fish 生成自动补全脚本。
✅ 正确:生成补全脚本
use clap::{CommandFactory, Parser};
use clap_complete::{generate, shells::Zsh};
use std::io;
fn print_zsh_completions() {
let mut cmd = super::Args::command();
generate(Zsh, &mut cmd, "mytool", &mut io::stdout());
}
main 函数中解析一次,然后将类型化的配置向下传递。unwrap 隐藏失败;应返回稳定的退出码和结构化的错误信息。每周安装量
63
代码仓库
GitHub 星标数
18
首次出现
2026年1月23日
安全审计
安装于
gemini-cli48
codex48
claude-code48
opencode47
cursor44
github-copilot44
Clap provides declarative command-line parsing with strong help output, validation, and subcommand support. Use it to build CLIs with predictable UX and testable execution paths.
✅ Correct: derive Parser
use clap::Parser;
#[derive(Parser, Debug)]
#[command(name = "mytool", version, about = "Example CLI")]
struct Args {
/// Enable verbose output
#[arg(long)]
verbose: bool,
/// Input file path
#[arg(value_name = "FILE")]
input: String,
}
fn main() {
let args = Args::parse();
if args.verbose {
eprintln!("verbose enabled");
}
println!("input={}", args.input);
}
❌ Wrong: parse multiple times
fn main() {
let _a = Args::parse();
let _b = Args::parse(); // duplicate parsing and inconsistent behavior
}
Model multi-mode CLIs with subcommands and shared global flags.
✅ Correct: global flags + subcommands
use clap::{Parser, Subcommand, ValueEnum};
#[derive(Parser, Debug)]
struct Args {
#[arg(long, global = true)]
verbose: bool,
#[arg(long, global = true, env = "MYTOOL_CONFIG")]
config: Option<String>,
#[command(subcommand)]
cmd: Command,
}
#[derive(Subcommand, Debug)]
enum Command {
Serve { #[arg(long, default_value_t = 3000)] port: u16 },
Migrate { #[arg(long, value_enum, default_value_t = Mode::Up)] mode: Mode },
}
#[derive(Copy, Clone, Debug, ValueEnum)]
enum Mode { Up, Down }
fn main() {
let args = Args::parse();
match args.cmd {
Command::Serve { port } => println!("serve on {}", port),
Command::Migrate { mode } => println!("migrate: {:?}", mode),
}
}
Prefer explicit precedence:
✅ Correct: merge config with CLI overrides
use clap::Parser;
use serde::Deserialize;
#[derive(Parser, Debug)]
struct Args {
#[arg(long, env = "APP_PORT")]
port: Option<u16>,
}
#[derive(Deserialize)]
struct FileConfig {
port: Option<u16>,
}
fn effective_port(args: &Args, file: &FileConfig) -> u16 {
args.port.or(file.port).unwrap_or(3000)
}
Map failures to stable exit codes. Return Result from command handlers and centralize printing.
✅ Correct: command returns Result
use std::process::ExitCode;
fn main() -> ExitCode {
match run() {
Ok(()) => ExitCode::SUCCESS,
Err(e) => {
eprintln!("{e}");
ExitCode::from(1)
}
}
}
fn run() -> Result<(), String> {
Ok(())
}
Test the binary surface (arguments, output, exit codes) without coupling to internals.
✅ Correct: integration test
use assert_cmd::Command;
#[test]
fn shows_help() {
Command::cargo_bin("mytool")
.unwrap()
.arg("--help")
.assert()
.success();
}
Generate completions for Bash/Zsh/Fish.
✅ Correct: emit completions
use clap::{CommandFactory, Parser};
use clap_complete::{generate, shells::Zsh};
use std::io;
fn print_zsh_completions() {
let mut cmd = super::Args::command();
generate(Zsh, &mut cmd, "mytool", &mut io::stdout());
}
main and pass a typed config down.unwrap; return stable exit codes and structured errors.Weekly Installs
63
Repository
GitHub Stars
18
First Seen
Jan 23, 2026
Security Audits
Gen Agent Trust HubPassSocketPassSnykPass
Installed on
gemini-cli48
codex48
claude-code48
opencode47
cursor44
github-copilot44
React 组合模式指南:Vercel 组件架构最佳实践,提升代码可维护性
120,000 周安装