Search code examples
rustclap

Rust Clap custom headings


I am using the rust Clap library to parse command line arguments. When displaying my help text I want to separate required arguments from optional arguments and put them under separate headings. Something along the lines of this:

HELP:
    Example header 1:
        Arg 1
        Arg 2

    Example header 2:
        Arg 3
        Arg 4

Is this possible.

After reading this, this and this I think it might be but I am not confident of how to go about doing so.

EDIT:
So a commentor has asked me to update the post with some desired output so below is an example from one of the links above. I would like to be able to have two options sections and name them.

$ myprog --help
My Super Program 1.0
Kevin K. <kbknapp@gmail.com>
Does awesome things

USAGE:
    MyApp [FLAGS] [OPTIONS] <INPUT> [SUBCOMMAND]

FLAGS:
    -h, --help       Prints this message
    -v               Sets the level of verbosity
    -V, --version    Prints version information

OPTIONS:
    -c, --config <FILE>    Sets a custom config file

ARGS:
    INPUT    The input file to use

SUBCOMMANDS:
    help    Prints this message
    test    Controls testing features

So changing the OPTIONS section above to be:

OPTIONS-1:
    -c, --config <FILE>    Sets a custom config file.

OPTIONS-2:
    -a, --another <FILE>    Another example command.

Solution

  • I think you might be looking for help_heading. It seems this has been added recently, so you'll have to grab the very latest commit.

    cargo.toml

    [dependencies]
    clap = { git = "https://github.com/clap-rs/clap", rev = "8145717" }
    

    main.rs

    use clap::Clap;
    
    #[derive(Clap, Debug)]
    #[clap(
        name = "My Application",
        version = "1.0",
        author = "Jason M.",
        about = "Stack Overflow"
    )]
    struct Opts {
        #[clap(
            help_heading = Some("OPTIONS-1"),
            short,
            long,
            value_name="FILE",
            about = "Sets a custom config file"
        )]
        config: String,
        #[clap(
            help_heading = Some("OPTIONS-2"),
            short,
            long,
            value_name="FILE",
            about = "Another example command"
        )]
        another: String,
    }
    
    fn main() {
        let opts: Opts = Opts::parse();
    }
    
    use clap::{App, Arg};
    
    fn main() {
        let app = App::new("My Application")
            .version("1.0")
            .author("Jason M.")
            .about("Stack Overflow")
            .help_heading("OPTIONS-1")
            .arg(
                Arg::new("config")
                    .short('c')
                    .long("config")
                    .value_name("FILE")
                    .about("Sets a custom config file"),
            )
            .help_heading("OPTIONS-2")
            .arg(
                Arg::new("another")
                    .short('a')
                    .long("another")
                    .value_name("FILE")
                    .about("Another example command"),
            );
    
        app.get_matches();
    }
    

    Either of the above will generate the following upon running cargo run -- --help:

    My Application 1.0
    Jason M.
    Stack Overflow
    
    USAGE:
        clap_headings --config <FILE> --another <FILE>
    
    FLAGS:
        -h, --help       Prints help information
        -V, --version    Prints version information
    
    OPTIONS-1:
        -c, --config <FILE>    Sets a custom config file
    
    OPTIONS-2:
        -a, --another <FILE>    Another example command