Argy
Argy: Command-line parsing library for modern C++ — simple, intuitive, and header-only with no dependencies.
Install / Use
/learn @mshenoda/ArgyREADME
Argy: Command-Line Argument Parsing Library for Modern C++<br> Because life's too short to parse argv by hand!
</div> <p align="center"> <a href="LICENSE"> <img src="https://img.shields.io/github/license/mshenoda/argy?color=blue" alt="License"/> </a> <a href="https://github.com/mshenoda/argy/releases"> <img src="https://img.shields.io/github/v/tag/mshenoda/argy?label=release" alt="Release"/> </a> <a href="https://github.com/mshenoda/argy/actions/workflows/ci-linux.yml"> <img src="https://img.shields.io/github/actions/workflow/status/mshenoda/argy/ci-linux.yml?label=Linux&logo=linux" alt="Linux Build"/> </a> <a href="https://github.com/mshenoda/argy/actions/workflows/ci-windows.yml"> <img src="https://img.shields.io/github/actions/workflow/status/mshenoda/argy/ci-windows.yml?label=Windows&logo=windows" alt="Windows Build"/> </a> <a href="https://github.com/mshenoda/argy/actions/workflows/ci-macos.yml"> <img src="https://img.shields.io/github/actions/workflow/status/mshenoda/argy/ci-macos.yml?label=macOS&logo=apple" alt="macOS Build"/> </a> <a href="https://github.com/mshenoda/argy/actions/workflows/ci-freebsd.yml"> <img src="https://img.shields.io/github/actions/workflow/status/mshenoda/argy/ci-freebsd.yml?label=FreeBSD&logo=freebsd" alt="FreeBSD Build"/> </a> <p align="center"> <a href="https://godbolt.org/z/P8xj3xfYW" target="_blank" rel="noopener noreferrer"> <img src="https://img.shields.io/badge/Godbolt-Demo-blue?logo=compilerexplorer" alt="Try Online"/> </a> </p> </p>Argy
Effortless, intuitive, and lightweight command-line argument parsing for C++17 and newer. Argy is a header-only library with zero dependencies, designed to make CLI development simple and type-safe.
If you love Python's argparse, you'll feel right at home—Argy brings that developer-friendly experience to C++.
Perfect for building robust, maintainable command-line tools in modern C++.
✨ Features
- 📦 Header-only & zero dependencies, just
#include "argy.hpp"and go - 🧩 Intuitive API for defining and parsing command-line arguments.
- 🎯 Argument Types Supports positional, optional, and flag arguments
- 🔄 Flexible Naming: Support for multiple aliases per argument (e.g.,
-v,--verbose,--debug-mode) - 🔒 Type-safe access to parsed values
- 📋 List Support: Native support for vector arguments with validation
- 🛡️ Built-in Validation: Rich set of validators for common patterns (emails, URLs, file paths, ranges, etc.) with fluent API
- 🎨 Beautiful Help: Auto-generated colorized help messages that look professional out of the box
- 🎪 Python-like Experience: Familiar API if you've used Python's argparse
- ⚡ POSIX Support: Support for
--separator to treat remaining arguments as positional
Demo:
🌐 Try Argy in your browser on Compiler Explorer!
📦 Installation
CMake (Recommended)
With FetchContent:
include(FetchContent)
FetchContent_Declare(
argy
GIT_REPOSITORY https://github.com/mshenoda/argy.git
GIT_TAG main # or a specific tag/release
)
FetchContent_MakeAvailable(argy)
target_link_libraries(your_target PRIVATE argy)
Header-Only (Any C++ Project Type)
Simply copy include/argy.hpp into your project and #include "argy.hpp".
🚀 Quick Start
#include <iostream>
#include "argy.hpp"
int main(int argc, char* argv[]) {
Argy::CliParser cli(argc, argv);
// Define arguments
cli.addString("input", "Input file path");
cli.addInt({"-n", "--count"}, "Number of items", 10);
cli.addBool({"-v", "--verbose"}, "Enable verbose output");
// Parse and use parsed args
auto args = cli.parse();
std::cout << "Input: " << args.getString("input") << "\n";
std::cout << "Count: " << args.getInt("count") << "\n";
std::cout << "Verbose: " << (args.getBool("verbose") ? "true" : "false") << "\n";
return 0;
}
That's it! Compile and run:
./my_app input.txt --count 42 --verbose
📖 API Guide
Argy offers two equivalent APIs - choose the one you prefer:
Template API (Type-Safe)
cli.add<std::string>("file", "Input file"); // Positional
cli.add<int>({"-n", "--count"}, "Number of items", 10); // Optional with default
cli.add<bool>({"-v", "--verbose"}, "Enable verbose output"); // Flag
auto args = cli.parse();
auto file = args.get<std::string>("file");
auto count = args.get<int>("count");
auto verbose = args.get<bool>("verbose");
Named Methods API (Explicit)
cli.addString("file", "Input file"); // Positional
cli.addInt({"-n", "--count"}, "Number of items", 10); // Optional with default
cli.addBool({"-v", "--verbose"}, "Enable verbose output"); // Flag
auto args = cli.parse();
auto file = args.getString("file");
auto count = args.getInt("count");
auto verbose = args.getBool("verbose");
Supported Types
| Type | Template API | Named API | Example |
|------|-------------|-----------|---------|
| String | add<std::string>() | addString() | "hello" |
| Integer | add<int>() | addInt() | 42 |
| Float | add<float>() | addFloat() | 3.14f |
| Boolean | add<bool>() | addBool() | true |
| String List | add<Argy::Strings>() | addStrings() | {"a", "b", "c"} |
| Integer List | add<Argy::Ints>() | addInts() | {1, 2, 3} |
| Float List | add<Argy::Floats>() | addFloats() | {1.0f, 2.0f} |
| Boolean List | add<Argy::Bools>() | addBools() | {true, false} |
🛡️ Built-in Validation (Fluent API)
Argy provides rich validation capabilities with a fluent API for robust argument parsing:
Basic Validators
// Range validation
cli.addInt({"-p", "--port"}, "Port number", 8080).isInRange(1024, 65535);
// Choice validation
cli.addString({"-m", "--mode"}, "Processing mode", "normal").isOneOf({"normal", "fast", "debug"});
// Regex validation
cli.add<std::string>({"-t", "--token"}, "API token").isMatch(R"([A-Za-z0-9]{32})");
String Pattern Validators
// Common patterns
cli.addString({"-e", "--email"}, "Email address").isEmail();
cli.addString({"-u", "--url"}, "API endpoint").isUrl();
cli.addString({"--ip"}, "Server IP").isIPAddress();
cli.addString({"--mac"}, "MAC address").isMACAddress();
cli.addString({"--uuid"}, "UUID").isUUID();
// Character type validation
cli.addString({"--alpha"}, "Alphabet letters only").isAlpha();
cli.addString({"--numeric"}, "Numbers only").isNumeric();
cli.addString({"--alphanum"}, "Alphanumeric").isAlphaNumeric();
File System Validators
cli.addString({"-f", "--file"}, "Input file").isFile();
cli.addString({"-d", "--dir"}, "Output directory").isDirectory();
cli.addString({"-p", "--path"}, "File or directory").isPath();
Vector Validation
// Validate all elements in a vector
cli.addInts({"-i", "--ids"}, "User IDs").isInRange(1, 1000000);
Custom Validators
// Custom validation lambda function
cli.addFloats({"-r", "--ratio"}, "Ratio value")
.validate([](const std::string& name, float value) {
if (value < 0.0f || value > 1.0f) {
throw Argy::InvalidValueException("Ratio must be between 0.0 and 1.0");
}
});
📋 Complete Examples
Real-World Example: Image Processing Tool
#include "argy.hpp"
#include <iostream>
int main(int argc, char* argv[]) {
Argy::CliParser cli(argc, argv);
try {
// Positional arguments (required)
cli.addString("input", "Input image path").isFile();
// Optional arguments with defaults
cli.addString({"-o", "--output"}, "Output directory", "./results/").isDirectory();
cli.addInt({"-q", "--quality"}, "JPEG quality (1-100)", 85).isInRange(1, 100);
cli.addString({"-f", "--format"}, "Output format", "jpg").isOneOf({"jpg", "png", "webp", "tiff"});
// Flags (boolean)
cli.addBool({"-v", "--verbose"}, "Enable verbose output");
cli.addBool({"-p", "--preview"}, "Generate preview images");
// Vector arguments
cli.addInts({"-s", "--sizes"}, "Output sizes", Argy::Ints{800, 1200}).isInRange(100, 10000);
cli.addStrings({"-t", "--tags"}, "Image tags", Argy::Strings{"processed"});
// Parse command line
cli.parse();
// Use parsed values
std::cout << "Processing: " << cli.getString("input") << "\n";
std::cout << "Output: " << cli.getString("output") << "\n";
std::cout << "Quality: " << cli.getInt("quality") << "%\n";
std::cout << "Format: " << cli.getString("format") << "\n";
if (cli.getBool("verbose")) {
std::cout << "Verbose mode enabled\n";
}
auto sizes = cli.getInts("sizes");
std::cout << "Output sizes: ";
for (auto size : sizes) std::cout << size << "px ";
std::cout << "\n";
} catch (const Argy::Exception& ex) {
std::cerr << "Error: " << ex.what() << "\n";
cli.printHelp(argv[0]);
return 1;
}
return 0;
}
Usage examples:
# Basic usage
./image_tool input.jpg
# With options
./image_tool input.jpg --output ./processed --quality 95 --format png
# With verbose and multiple sizes
./image_tool input.jpg -v --sizes 400 800 1600 --tags "landscape" "hdr"
# Using POSIX -- separator for files with special names
./image_tool --verbose --quality 90 -- --weird-filename.jpg
./image_tool -o ./output -- input1.jpg input2.jpg
# Help
./image_tool --help
📺 Beautiful Help Output
Argy automatically generates beautiful, colorized help messages. When you run your program with --help or -h:
Usage: ./image_tool <input> [options]
Positional:
input
Related Skills
node-connect
348.2kDiagnose OpenClaw node connection and pairing failures for Android, iOS, and macOS companion apps
frontend-design
108.9kCreate distinctive, production-grade frontend interfaces with high design quality. Use this skill when the user asks to build web components, pages, or applications. Generates creative, polished code that avoids generic AI aesthetics.
openai-whisper-api
348.2kTranscribe audio via OpenAI Audio Transcriptions API (Whisper).
qqbot-media
348.2kQQBot 富媒体收发能力。使用 <qqmedia> 标签,系统根据文件扩展名自动识别类型(图片/语音/视频/文件)。
