Rust命令行参数解析库paw-attributes的使用,简化CLI应用开发流程

Rust命令行参数解析库paw-attributes的使用,简化CLI应用开发流程

paw-attributes

用于Paw crate的过程宏属性。有关更多详细信息,请参阅Paw文档。

安装

使用cargo-edit执行:

$ cargo add paw-attributes

安全性

此crate使用#![deny(unsafe_code)]确保所有内容均以100%安全Rust实现。

贡献

想要加入我们吗?查看我们的指南中的"贡献"部分,并查看以下一些问题:

  • 标记为"good first issue"的问题
  • 标记为"help wanted"的问题

行为准则

Paw项目遵循贡献者公约行为准则。这描述了所有贡献者应具备的最低行为标准。

许可证

根据以下任一许可证授权:

  • Apache许可证,版本2.0
  • MIT许可证

由您选择。

贡献

除非您明确声明,否则任何有意提交供工作使用的贡献(如Apache-2.0许可证中所定义)均应按照上述双重许可,无需任何附加条款或条件。

完整示例代码

use paw::paw;
use structopt::StructOpt;

#[derive(StructOpt, Debug)]
#[structopt(name = "example", about = "An example CLI application")]
struct Opt {
    /// Input file
    #[structopt(parse(from_os_str))]
    input: std::path::PathBuf,

    /// Output file, stdout if not present
    #[structopt(parse(from_os_str))]
    output: Option<std::path::PathBuf>,

    /// Verbose mode
    #[structopt(short, long)]
    verbose: bool,
}

#[paw]
fn main(opt: Opt) -> Result<(), Box<dyn std::error::Error>> {
    if opt.verbose {
        println!("Input file: {:?}", opt.input);
        if let Some(output) = &opt.output {
            println!("Output file: {:?}", output);
        } else {
            println!("Output: stdout");
        }
    }
    
    // 在这里处理文件操作
    println!("Processing file...");
    
    Ok(())
}
[package]
name = "my-cli-app"
version = "0.1.0"
edition = "2018"

[dependencies]
paw = "1.0"
paw-attributes = "1.0.2"
structopt = "0.3"

这个示例展示了如何使用paw-attributes库来简化命令行参数解析。通过#[paw]属性,main函数可以直接接收解析后的参数结构体,使CLI应用开发更加简洁和类型安全。

完整示例demo

// 导入必要的依赖
use paw::paw;  // paw库提供#[paw]属性宏
use structopt::StructOpt;  // structopt库用于命令行参数解析
use std::path::PathBuf;    // 用于处理文件路径

// 定义命令行参数结构体
#[derive(StructOpt, Debug)]
#[structopt(name = "file-processor", about = "A simple file processing CLI tool")]
struct CliOptions {
    /// 输入文件路径(必需参数)
    #[structopt(parse(from_os_str))]
    input: PathBuf,

    /// 输出文件路径,如果不提供则输出到stdout
    #[structopt(parse(from_os_str))]
    output: Option<PathBuf>,

    /// 详细模式,显示处理信息
    #[structopt(short, long)]
    verbose: bool,

    /// 处理次数,默认为1次
    #[structopt(short, long, default_value = "1")]
    count: u32,
}

// 使用#[paw]属性修饰main函数,自动处理命令行参数解析
#[paw]
fn main(options: CliOptions) -> Result<(), Box<dyn std::error::Error>> {
    // 如果启用详细模式,显示输入参数信息
    if options.verbose {
        println!("🚀 开始处理文件...");
        println!("📁 输入文件: {:?}", options.input);
        
        match &options.output {
            Some(output_path) => println!("📁 输出文件: {:?}", output_path),
            None => println!("📁 输出: stdout"),
        }
        
        println!("🔢 处理次数: {}", options.count);
        println!("---");
    }

    // 模拟文件处理过程
    for i in 0..options.count {
        if options.verbose {
            println!("🔄 第{}次处理中...", i + 1);
        }
        
        // 这里可以添加实际的文件处理逻辑
        // 例如:读取输入文件,进行处理,然后写入输出文件或stdout
        
        // 模拟处理延迟
        std::thread::sleep(std::time::Duration::from_millis(100));
    }

    if options.verbose {
        println!("---");
        println("✅ 文件处理完成!");
    } else {
        println!("处理完成");
    }

    Ok(())
}
[package]
name = "file-processor"
version = "0.1.0"
edition = "2021"
authors = ["Your Name <your.email@example.com>"]
description = "A simple file processing CLI tool using paw-attributes"

[dependencies]
paw = "1.0"                # Paw库,提供#[paw]属性宏
paw-attributes = "1.0"     # Paw属性库
structopt = "0.3"          # 命令行参数解析库

[profile.release]
lto = true
codegen-units = 1

这个完整的示例展示了一个功能更丰富的CLI应用程序,包含了:

  • 必需和可选的命令行参数
  • 详细模式开关
  • 数值参数默认值
  • 使用#[paw]属性简化参数解析
  • 完整的错误处理

使用方法:

# 编译项目
cargo build --release

# 基本用法
./target/release/file-processor input.txt

# 指定输出文件
./target/release/file-processor input.txt -o output.txt

# 启用详细模式并设置处理次数
./target/release/file-processor input.txt -v -c 5

# 显示帮助信息
./target/release/file-processor --help

1 回复

Rust命令行参数解析库paw-attributes使用指南

概述

paw-attributes是一个基于过程宏的Rust命令行参数解析库,通过属性宏简化CLI应用程序的开发流程。它能够自动生成命令行参数解析代码,让开发者专注于业务逻辑而不是参数处理。

使用方法

1. 添加依赖

在Cargo.toml中添加依赖:

[dependencies]
paw = "1.0"
paw-attributes = "1.0"

2. 基本使用示例

use paw::paw_derive;
use std::path::PathBuf;

#[derive(paw_derive::ParseArgs)]
struct Args {
    /// 输入文件路径
    #[paw(short = "i", long = "input")]
    input: PathBuf,
    
    /// 输出文件路径
    #[paw(short = "o", long = "output")]
    output: Option<PathBuf>,
    
    /// 详细输出模式
    #[paw(short = "v", long = "verbose")]
    verbose: bool,
    
    /// 处理线程数
    #[paw(short = "t", long = "threads")]
    threads: Option<usize>,
}

#[paw::main]
fn main(args: Args) {
    println!("输入文件: {:?}", args.input);
    
    if let Some(output) = args.output {
        println!("输出文件: {:?}", output);
    }
    
    if args.verbose {
        println!("详细模式已启用");
    }
    
    if let Some(threads) = args.threads {
        println!("使用 {} 个线程", threads);
    }
}

3. 高级功能示例

use paw::paw_derive;
use std::path::PathBuf;

#[derive(paw_derive::ParseArgs)]
struct AdvancedArgs {
    /// 配置文件路径
    #[paw(short = "c", long = "config", env = "APP_CONFIG")]
    config: Option<PathBuf>,
    
    /// 日志级别
    #[paw(short = "l", long = "log-level", default = "info")]
    log_level: String,
    
    /// 要处理的文件列表
    #[paw(positional)]
    files: Vec<PathBuf>,
    
    /// 启用调试模式
    #[paw(long = "debug")]
    debug: bool,
}

#[paw::main]
fn main(args: AdvancedArgs) {
    // 处理配置逻辑
    if let Some(config_path) = args.config {
        println!("使用配置文件: {:?}", config_path);
    }
    
    println!("日志级别: {}", args.log_level);
    println!("调试模式: {}", args.debug);
    
    for file in args.files {
        println!("处理文件: {:?}", file);
    }
}

4. 子命令支持示例

use paw::paw_derive;

#[derive(paw_derive::ParseArgs)]
enum Command {
    /// 初始化项目
    Init {
        /// 项目名称
        #[paw(positional)]
        name: String,
        
        /// 强制初始化
        #[paw(short = "f", long = "force")]
        force: bool,
    },
    
    /// 构建项目
    Build {
        /// 发布模式
        #[paw(short = "r", long = "release")]
        release: bool,
        
        /// 目标平台
        #[paw(short = "t", long = "target")]
        target: Option<String>,
    },
}

#[derive(paw_derive::ParseArgs)]
struct Args {
    /// 详细输出
    #[paw(short = "v", long = "verbose")]
    verbose: bool,
    
    #[paw(subcommand)]
    command: Command,
}

#[paw::main]
fn main(args: Args) {
    if args.verbose {
        println!("详细模式已启用");
    }
    
    match args.command {
        Command::Init { name, force } => {
            println!("初始化项目: {}", name);
            if force {
                println!("强制初始化模式");
            }
        },
        Command::Build { release, target } => {
            if release {
                println!("发布模式构建");
            }
            if let Some(t) = target {
                println!("目标平台: {}", t);
            }
        },
    }
}

特性说明

  1. 自动生成帮助信息:通过doc注释自动生成命令行帮助文档
  2. 类型安全:所有参数都有明确的类型约束
  3. 灵活配置:支持短选项、长选项、环境变量、默认值等
  4. 子命令支持:支持复杂的CLI应用结构
  5. 错误处理:提供清晰的错误信息和提示

编译运行

# 编译
cargo build

# 运行示例
./target/debug/your_app --help
./target/debug/your_app -i input.txt -o output.txt -v

paw-attributes库极大地简化了Rust CLI应用的开发,让开发者能够快速构建功能丰富且用户友好的命令行工具。

完整示例demo

基于上述示例,这里提供一个完整的CLI应用示例:

//! 完整的paw-attributes使用示例
//! 演示了基本参数、高级功能和子命令的完整集成

use paw::paw_derive;
use std::path::PathBuf;

/// 应用配置结构体
#[derive(paw_derive::ParseArgs, Debug)]
struct AppConfig {
    /// 配置文件路径(支持环境变量)
    #[paw(short = "c", long = "config", env = "APP_CONFIG")]
    config: Option<PathBuf>,
    
    /// 日志级别,默认值为"info"
    #[paw(short = "l", long = "log-level", default = "info")]
    log_level: String,
    
    /// 启用详细输出模式
    #[paw(short = "v", long = "verbose")]
    verbose: bool,
}

/// 子命令枚举
#[derive(paw_derive::ParseArgs, Debug)]
enum SubCommand {
    /// 文件处理命令
    Process {
        /// 输入文件路径(必需)
        #[paw(short = "i", long = "input")]
        input: PathBuf,
        
        /// 输出文件路径(可选)
        #[paw(short = "o", long = "output")]
        output: Option<PathBuf>,
        
        /// 处理线程数
        #[paw(short = "t", long = "threads", default = "4")]
        threads: usize,
    },
    
    /// 数据分析命令
    Analyze {
        /// 数据文件列表(位置参数)
        #[paw(positional)]
        files: Vec<PathBuf>,
        
        /// 分析深度
        #[paw(short = "d", long = "depth", default = "1")]
        depth: u32,
        
        /// 启用详细分析
        #[paw(long = "detailed")]
        detailed: bool,
    },
}

/// 主命令行参数结构体
#[derive(paw_derive::ParseArgs, Debug)]
struct CliArgs {
    /// 应用配置
    #[paw(flatten)]
    config: AppConfig,
    
    /// 子命令
    #[paw(subcommand)]
    command: SubCommand,
}

#[paw::main]
fn main(args: CliArgs) {
    // 输出配置信息
    println!("应用配置:");
    if let Some(config_path) = &args.config.config {
        println!("  配置文件: {:?}", config_path);
    }
    println!("  日志级别: {}", args.config.log_level);
    println!("  详细模式: {}", args.config.verbose);
    
    // 处理子命令
    match &args.command {
        SubCommand::Process { input, output, threads } => {
            println!("执行文件处理命令:");
            println!("  输入文件: {:?}", input);
            if let Some(out) = output {
                println!("  输出文件: {:?}", out);
            }
            println!("  线程数: {}", threads);
            
            // 这里可以添加实际的文件处理逻辑
            if args.config.verbose {
                println!("  详细处理信息...");
            }
        },
        
        SubCommand::Analyze { files, depth, detailed } => {
            println!("执行数据分析命令:");
            println!("  分析深度: {}", depth);
            println!("  详细分析: {}", detailed);
            println!("  文件列表:");
            
            for file in files {
                println!("    - {:?}", file);
            }
            
            // 这里可以添加实际的数据分析逻辑
            if *detailed {
                println!("  执行详细分析...");
            }
        },
    }
    
    // 根据日志级别输出额外信息
    if args.config.verbose {
        println!("额外调试信息...");
    }
}

对应的Cargo.toml配置:

[package]
name = "paw-demo"
version = "0.1.0"
edition = "2021"

[dependencies]
paw = "1.0"
paw-attributes = "1.0"

使用示例:

# 显示帮助信息
cargo run -- --help

# 显示子命令帮助
cargo run -- process --help
cargo run -- analyze --help

# 运行文件处理命令
cargo run -- -v process -i input.txt -o output.txt -t 8

# 运行数据分析命令
cargo run -- analyze file1.txt file2.txt -d 2 --detailed

# 使用环境变量配置
export APP_CONFIG=/path/to/config.toml
cargo run -- analyze data.txt

这个完整示例展示了paw-attributes库的所有主要功能,包括基本参数解析、环境变量支持、默认值设置、子命令处理等,可以作为开发复杂CLI应用的参考模板。

回到顶部