#arguments-parser #imperative #no-dependencies #implicit #no-macros #help-text

noargs

Imperative command-line argument parser library with no dependencies, no macros, and no implicit I/O

12 releases

Uses new Rust 2024

0.4.3 Apr 29, 2026
0.4.2 Jan 10, 2026
0.4.1 Jun 19, 2025
0.3.2 Apr 17, 2025
0.0.1 Mar 23, 2025

#100 in Command-line interface

Download history 2829/week @ 2026-01-25 1419/week @ 2026-02-01 1504/week @ 2026-02-08 1098/week @ 2026-02-15 574/week @ 2026-02-22 400/week @ 2026-03-01 639/week @ 2026-03-08 729/week @ 2026-03-15 1443/week @ 2026-03-22 1089/week @ 2026-03-29 381/week @ 2026-04-05 419/week @ 2026-04-12 481/week @ 2026-04-19 444/week @ 2026-04-26 377/week @ 2026-05-03 400/week @ 2026-05-10

1,791 downloads per month
Used in 30 crates

MIT license

92KB
2K SLoC

noargs

noargs Documentation Actions Status License

noargs is an imperative command-line argument parser library for Rust with no dependencies, no macros, and no implicit I/O.

Features

  • Supports the following argument types:
    • Positional arguments (Arg)
    • Named arguments with values (Opt)
    • Named arguments without values (Flag)
    • Subcommands (Cmd)
  • Automatically generates help text
  • Simple and minimal interface due to its imperative nature (no complex DSL)

Examples

Basic Usage

The following code demonstrates the basic usage of noargs:

fn main() -> noargs::Result<()> {
    // Create `noargs::RawArgs` having the result of `std::env::args()`.
    let mut args = noargs::raw_args();

    // Set metadata for help
    args.metadata_mut().app_name = env!("CARGO_PKG_NAME");
    args.metadata_mut().app_description = env!("CARGO_PKG_DESCRIPTION");

    // Handle well-known flags
    if noargs::VERSION_FLAG.take(&mut args).is_present() {
        println!("{} {}", env!("CARGO_PKG_NAME"), env!("CARGO_PKG_VERSION"));
        return Ok(());
    }
    noargs::HELP_FLAG.take_help(&mut args);

    // Handle application specific args
    let foo: usize = noargs::opt("foo")
        .default("1").take(&mut args).then(|o| o.value().parse())?;
    let bar: bool = noargs::flag("bar")
        .take(&mut args).is_present();
    let baz: Option<String> = noargs::arg("[BAZ]")
        .take(&mut args).present_and_then(|a| a.value().parse())?;

    // Check unexpected args and build help text if need
    if let Some(help) = args.finish()? {
        print!("{help}");
        return Ok(());
    }

    // Do application logic
    println!("foo: {}, bar: {}, baz: {:?}", foo, bar, baz);

    Ok(())
}

For a fuller no-subcommand example (with common pitfalls), see examples/basics.rs. For repeated options / positional arrays, see examples/arrays.rs.

Subcommands

The following example shows how to handle subcommands. For a fuller command-routing pattern, see examples/subcommands.rs.

fn main() -> noargs::Result<()> {
    let mut args = noargs::raw_args();
    args.metadata_mut().app_name = env!("CARGO_PKG_NAME");
    args.metadata_mut().app_description = env!("CARGO_PKG_DESCRIPTION");

    // Handle well-known flags
    if noargs::VERSION_FLAG.take(&mut args).is_present() {
        println!("{} {}", env!("CARGO_PKG_NAME"), env!("CARGO_PKG_VERSION"));
        return Ok(());
    }
    noargs::HELP_FLAG.take_help(&mut args);

    // Handle subcommands
    if noargs::cmd("start")
        .doc("Start the service")
        .take(&mut args)
        .is_present()
    {
        let port: u16 = noargs::opt("port")
            .short('p')
            .default("8080")
            .take(&mut args)
            .then(|o| o.value().parse())?;
        println!("Starting service on port {}", port);
    } else if noargs::cmd("stop")
        .doc("Stop the service")
        .take(&mut args)
        .is_present()
    {
        println!("Stopping service");
    } else if let Some(help) = args.finish()? {
        print!("{help}");
    }

    Ok(())
}

No runtime deps