Command-line apps

Why Rust?

Shield with a checkmark

Solid and quick

Even if you’re just writing a short one-off script, you can be confident it’s fast, easily testable, and gives helpful output.

Rust’s guarantees
box with a checkmark

Easy distribution

Compile everything down to a single binary—no need for your users to have a runtime or libraries installed.

How to ship Rust code
A note and a gear

Robust configuration

Handle configuration files across platforms with ease. Rust will deal with namespaces and formats for you.

Start configuring
Help manual

Manuals? done.

Generate manual pages for your app automatically. Just package the generated files and you’re done.

Learn how
Pipes

Data in, data out

In addition to talking to humans, Rust has great tools to help you talk to machines.

Communicate with machines
3 wood logs stacked on top of each other

Flexible logging

It’s easy to add logging, and even easier to configure it to different targets and with different styles.

Log, trace, comprehend

A maintainable code base

cli app structure

Catch errors now

What if the config file is missing or corrupt? What if the content of that one environment variable is empty? These cases are easy to forget about! But thanks to its approach to error handling and its library design, Rust will point out these “what if” situations before you even run your program.

Rust’s error handling
cli is no rocket science

Easily extend later

Rust allows you to be flexible in the way you organize your code. Start with just a single file and, when you need more features, refactor your application with the confidence that you aren’t breaking anything.

Refactoring Rust

Get started!

Writing a command-line app is a great way to learn Rust.

Define your inputs

use clap::Parser;

/// Read some lines of a file
#[derive(Debug, Parser)]
struct Cli {
    /// Input file to read
    file: String,
    /// Number of lines to read
    #[structopt(short = 'n')]
    num: usize,
}

Write your tool

use std::{error::Error, fs::read_to_string};

fn main() -> Result<(), Box> {
    let args = Cli::parse();
    read_to_string(&args.file)?
        .lines()
        .take(args.num)
        .for_each(|line| println!("{}", line));
    Ok(())
}
Learn more with the CLI book

Production use

sentry logo
One of the reasons we liked Rust was the crates.io ecosystem. [...] There is a lot of really good already existing infrastructure for building very nice command-line interfaces.

– Armin Ronacher, Rust at Sentry – PolyConf 2017


I have zero regrets with living in this code base. […] This was sort of an added bonus for me: Using Rust to make CLI or console based tools. It is very good at compiling for different target systems.

– Fletcher Nichol, Taking Rust to Production – RustFest Kyiv

Habitat logo