From 9f1a306962078ba0ae4e7dcc5c7958fcb3c6cba1 Mon Sep 17 00:00:00 2001 From: Alex Gorevski Date: Thu, 19 Feb 2026 11:42:31 -0800 Subject: [PATCH] docs(cli): add detailed help text and examples to complex subcommands Add long_about attributes with usage examples to the following commands: src/main.rs (binary CLI): - Agent: interactive/single-message modes, provider/peripheral options - Gateway: port/host binding with examples - Daemon: full runtime explanation with service install reference - Cron: cron expression format, timezone handling, all scheduling modes - Channel: supported types, JSON config format, bind-telegram - Hardware: discover, introspect, info subcommands - Peripheral: add, flash, board types - Config: schema export src/lib.rs (library enums): - CronCommands::Add: cron syntax and timezone examples - CronCommands::AddAt: RFC 3339 timestamp format - CronCommands::AddEvery: interval in milliseconds - CronCommands::Once: human-readable duration syntax - CronCommands::Update: partial field update - ChannelCommands::Add: JSON config and supported types - ChannelCommands::BindTelegram: username/numeric ID format - HardwareCommands::Discover, Introspect, Info: device paths and chip names - PeripheralCommands::Add: board types and transport paths - PeripheralCommands::Flash: serial port options Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- src/lib.rs | 115 ++++++++++++++++++++++++++++++++++++++++++++++++++++ src/main.rs | 104 +++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 219 insertions(+) diff --git a/src/lib.rs b/src/lib.rs index 600fa1d..53cda14 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -96,6 +96,17 @@ pub enum ChannelCommands { /// Run health checks for configured channels (handled in main.rs for async) Doctor, /// Add a new channel configuration + #[command(long_about = "\ +Add a new channel configuration. + +Provide the channel type and a JSON object with the required \ +configuration keys for that channel type. + +Supported types: telegram, discord, slack, whatsapp, matrix, imessage, email. + +Examples: + zeroclaw channel add telegram '{\"bot_token\":\"...\",\"name\":\"my-bot\"}' + zeroclaw channel add discord '{\"bot_token\":\"...\",\"name\":\"my-discord\"}'")] Add { /// Channel type (telegram, discord, slack, whatsapp, matrix, imessage, email) channel_type: String, @@ -108,6 +119,16 @@ pub enum ChannelCommands { name: String, }, /// Bind a Telegram identity (username or numeric user ID) into allowlist + #[command(long_about = "\ +Bind a Telegram identity into the allowlist. + +Adds a Telegram username (without the '@' prefix) or numeric user \ +ID to the channel allowlist so the agent will respond to messages \ +from that identity. + +Examples: + zeroclaw channel bind-telegram zeroclaw_user + zeroclaw channel bind-telegram 123456789")] BindTelegram { /// Telegram identity to allow (username without '@' or numeric user ID) identity: String, @@ -152,6 +173,16 @@ pub enum CronCommands { /// List all scheduled tasks List, /// Add a new scheduled task + #[command(long_about = "\ +Add a new recurring scheduled task. + +Uses standard 5-field cron syntax: 'min hour day month weekday'. \ +Times are evaluated in UTC by default; use --tz with an IANA \ +timezone name to override. + +Examples: + zeroclaw cron add '0 9 * * 1-5' 'Good morning' --tz America/New_York + zeroclaw cron add '*/30 * * * *' 'Check system health'")] Add { /// Cron expression expression: String, @@ -162,6 +193,14 @@ pub enum CronCommands { command: String, }, /// Add a one-shot scheduled task at an RFC3339 timestamp + #[command(long_about = "\ +Add a one-shot task that fires at a specific UTC timestamp. + +The timestamp must be in RFC 3339 format (e.g. 2025-01-15T14:00:00Z). + +Examples: + zeroclaw cron add-at 2025-01-15T14:00:00Z 'Send reminder' + zeroclaw cron add-at 2025-12-31T23:59:00Z 'Happy New Year!'")] AddAt { /// One-shot timestamp in RFC3339 format at: String, @@ -169,6 +208,14 @@ pub enum CronCommands { command: String, }, /// Add a fixed-interval scheduled task + #[command(long_about = "\ +Add a task that repeats at a fixed interval. + +Interval is specified in milliseconds. For example, 60000 = 1 minute. + +Examples: + zeroclaw cron add-every 60000 'Ping heartbeat' # every minute + zeroclaw cron add-every 3600000 'Hourly report' # every hour")] AddEvery { /// Interval in milliseconds every_ms: u64, @@ -176,6 +223,16 @@ pub enum CronCommands { command: String, }, /// Add a one-shot delayed task (e.g. "30m", "2h", "1d") + #[command(long_about = "\ +Add a one-shot task that fires after a delay from now. + +Accepts human-readable durations: s (seconds), m (minutes), \ +h (hours), d (days). + +Examples: + zeroclaw cron once 30m 'Run backup in 30 minutes' + zeroclaw cron once 2h 'Follow up on deployment' + zeroclaw cron once 1d 'Daily check'")] Once { /// Delay duration delay: String, @@ -188,6 +245,15 @@ pub enum CronCommands { id: String, }, /// Update a scheduled task + #[command(long_about = "\ +Update one or more fields of an existing scheduled task. + +Only the fields you specify are changed; others remain unchanged. + +Examples: + zeroclaw cron update --expression '0 8 * * *' + zeroclaw cron update --tz Europe/London --name 'Morning check' + zeroclaw cron update --command 'Updated message'")] Update { /// Task ID id: String, @@ -230,13 +296,39 @@ pub enum IntegrationCommands { #[derive(Subcommand, Debug, Clone, Serialize, Deserialize, PartialEq, Eq)] pub enum HardwareCommands { /// Enumerate USB devices (VID/PID) and show known boards + #[command(long_about = "\ +Enumerate USB devices and show known boards. + +Scans connected USB devices by VID/PID and matches them against \ +known development boards (STM32 Nucleo, Arduino, ESP32). + +Examples: + zeroclaw hardware discover")] Discover, /// Introspect a device by path (e.g. /dev/ttyACM0) + #[command(long_about = "\ +Introspect a device by its serial or device path. + +Opens the specified device path and queries for board information, \ +firmware version, and supported capabilities. + +Examples: + zeroclaw hardware introspect /dev/ttyACM0 + zeroclaw hardware introspect COM3")] Introspect { /// Serial or device path path: String, }, /// Get chip info via USB (probe-rs over ST-Link). No firmware needed on target. + #[command(long_about = "\ +Get chip info via USB using probe-rs over ST-Link. + +Queries the target MCU directly through the debug probe without \ +requiring any firmware on the target board. + +Examples: + zeroclaw hardware info + zeroclaw hardware info --chip STM32F401RETx")] Info { /// Chip name (e.g. STM32F401RETx). Default: STM32F401RETx for Nucleo-F401RE #[arg(long, default_value = "STM32F401RETx")] @@ -250,6 +342,19 @@ pub enum PeripheralCommands { /// List configured peripherals List, /// Add a peripheral (board path, e.g. nucleo-f401re /dev/ttyACM0) + #[command(long_about = "\ +Add a peripheral by board type and transport path. + +Registers a hardware board so the agent can use its tools (GPIO, \ +sensors, actuators). Use 'native' as path for local GPIO on \ +single-board computers like Raspberry Pi. + +Supported boards: nucleo-f401re, rpi-gpio, esp32, arduino-uno. + +Examples: + zeroclaw peripheral add nucleo-f401re /dev/ttyACM0 + zeroclaw peripheral add rpi-gpio native + zeroclaw peripheral add esp32 /dev/ttyUSB0")] Add { /// Board type (nucleo-f401re, rpi-gpio, esp32) board: String, @@ -257,6 +362,16 @@ pub enum PeripheralCommands { path: String, }, /// Flash ZeroClaw firmware to Arduino (creates .ino, installs arduino-cli if needed, uploads) + #[command(long_about = "\ +Flash ZeroClaw firmware to an Arduino board. + +Generates the .ino sketch, installs arduino-cli if it is not \ +already available, compiles, and uploads the firmware. + +Examples: + zeroclaw peripheral flash + zeroclaw peripheral flash --port /dev/cu.usbmodem12345 + zeroclaw peripheral flash -p COM3")] Flash { /// Serial port (e.g. /dev/cu.usbmodem12345). If omitted, uses first arduino-uno from config. #[arg(short, long)] diff --git a/src/main.rs b/src/main.rs index 672e7e6..f66b664 100644 --- a/src/main.rs +++ b/src/main.rs @@ -130,6 +130,17 @@ enum Commands { }, /// Start the AI agent loop + #[command(long_about = "\ +Start the AI agent loop. + +Launches an interactive chat session with the configured AI provider. \ +Use --message for single-shot queries without entering interactive mode. + +Examples: + zeroclaw agent # interactive session + zeroclaw agent -m \"Summarize today's logs\" # single message + zeroclaw agent -p anthropic --model claude-sonnet-4-20250514 + zeroclaw agent --peripheral nucleo-f401re:/dev/ttyACM0")] Agent { /// Single message mode (don't enter interactive mode) #[arg(short, long)] @@ -153,6 +164,18 @@ enum Commands { }, /// Start the gateway server (webhooks, websockets) + #[command(long_about = "\ +Start the gateway server (webhooks, websockets). + +Runs the HTTP/WebSocket gateway that accepts incoming webhook events \ +and WebSocket connections. Bind address defaults to the values in \ +your config file (gateway.host / gateway.port). + +Examples: + zeroclaw gateway # use config defaults + zeroclaw gateway -p 8080 # listen on port 8080 + zeroclaw gateway --host 0.0.0.0 # bind to all interfaces + zeroclaw gateway -p 0 # random available port")] Gateway { /// Port to listen on (use 0 for random available port); defaults to config gateway.port #[arg(short, long)] @@ -164,6 +187,21 @@ enum Commands { }, /// Start long-running autonomous runtime (gateway + channels + heartbeat + scheduler) + #[command(long_about = "\ +Start the long-running autonomous daemon. + +Launches the full ZeroClaw runtime: gateway server, all configured \ +channels (Telegram, Discord, Slack, etc.), heartbeat monitor, and \ +the cron scheduler. This is the recommended way to run ZeroClaw in \ +production or as an always-on assistant. + +Use 'zeroclaw service install' to register the daemon as an OS \ +service (systemd/launchd) for auto-start on boot. + +Examples: + zeroclaw daemon # use config defaults + zeroclaw daemon -p 9090 # gateway on port 9090 + zeroclaw daemon --host 127.0.0.1 # localhost only")] Daemon { /// Port to listen on (use 0 for random available port); defaults to config gateway.port #[arg(short, long)] @@ -190,6 +228,25 @@ enum Commands { Status, /// Configure and manage scheduled tasks + #[command(long_about = "\ +Configure and manage scheduled tasks. + +Schedule recurring, one-shot, or interval-based tasks using cron \ +expressions, RFC 3339 timestamps, durations, or fixed intervals. + +Cron expressions use the standard 5-field format: \ +'min hour day month weekday'. Timezones default to UTC; \ +override with --tz and an IANA timezone name. + +Examples: + zeroclaw cron list + zeroclaw cron add '0 9 * * 1-5' 'Good morning' --tz America/New_York + zeroclaw cron add '*/30 * * * *' 'Check system health' + zeroclaw cron add-at 2025-01-15T14:00:00Z 'Send reminder' + zeroclaw cron add-every 60000 'Ping heartbeat' + zeroclaw cron once 30m 'Run backup in 30 minutes' + zeroclaw cron pause + zeroclaw cron update --expression '0 8 * * *' --tz Europe/London")] Cron { #[command(subcommand)] cron_command: CronCommands, @@ -205,6 +262,19 @@ enum Commands { Providers, /// Manage channels (telegram, discord, slack) + #[command(long_about = "\ +Manage communication channels. + +Add, remove, list, and health-check channels that connect ZeroClaw \ +to messaging platforms. Supported channel types: telegram, discord, \ +slack, whatsapp, matrix, imessage, email. + +Examples: + zeroclaw channel list + zeroclaw channel doctor + zeroclaw channel add telegram '{\"bot_token\":\"...\",\"name\":\"my-bot\"}' + zeroclaw channel remove my-bot + zeroclaw channel bind-telegram zeroclaw_user")] Channel { #[command(subcommand)] channel_command: ChannelCommands, @@ -235,18 +305,52 @@ enum Commands { }, /// Discover and introspect USB hardware + #[command(long_about = "\ +Discover and introspect USB hardware. + +Enumerate connected USB devices, identify known development boards \ +(STM32 Nucleo, Arduino, ESP32), and retrieve chip information via \ +probe-rs / ST-Link. + +Examples: + zeroclaw hardware discover + zeroclaw hardware introspect /dev/ttyACM0 + zeroclaw hardware info --chip STM32F401RETx")] Hardware { #[command(subcommand)] hardware_command: zeroclaw::HardwareCommands, }, /// Manage hardware peripherals (STM32, RPi GPIO, etc.) + #[command(long_about = "\ +Manage hardware peripherals. + +Add, list, flash, and configure hardware boards that expose tools \ +to the agent (GPIO, sensors, actuators). Supported boards: \ +nucleo-f401re, rpi-gpio, esp32, arduino-uno. + +Examples: + zeroclaw peripheral list + zeroclaw peripheral add nucleo-f401re /dev/ttyACM0 + zeroclaw peripheral add rpi-gpio native + zeroclaw peripheral flash --port /dev/cu.usbmodem12345 + zeroclaw peripheral flash-nucleo")] Peripheral { #[command(subcommand)] peripheral_command: zeroclaw::PeripheralCommands, }, /// Manage configuration + #[command(long_about = "\ +Manage ZeroClaw configuration. + +Inspect and export configuration settings. Use 'schema' to dump \ +the full JSON Schema for the config file, which documents every \ +available key, type, and default value. + +Examples: + zeroclaw config schema # print JSON Schema to stdout + zeroclaw config schema > schema.json")] Config { #[command(subcommand)] config_command: ConfigCommands,