Skip to content

chore(deps): update dependency jdx/usage to v6 - #29

Open
renovate[bot] wants to merge 1 commit into
mainfrom
renovate/jdx-usage-6.x
Open

chore(deps): update dependency jdx/usage to v6#29
renovate[bot] wants to merge 1 commit into
mainfrom
renovate/jdx-usage-6.x

Conversation

@renovate

@renovate renovate Bot commented Aug 22, 2026

Copy link
Copy Markdown
Contributor

ℹ️ Note

This PR body was truncated due to platform limits.

This PR contains the following updates:

Package Update Change
jdx/usage major 2.18.26.6.1

Warning

Some dependencies could not be looked up. Check the Dependency Dashboard for more information.


Release Notes

jdx/usage (jdx/usage)

v6.6.1: : Cleaner plain help and smarter flag completion

Compare Source

A small bugfix release focused on help rendering and shell completion. Plain help output no longer leaks embedded ANSI escapes, root-only help metadata stays on the root page, and completion now handles attached --flag=value syntax.

Fixed

  • (complete) Complete attached long flag values (#​1349, @​nfvelten). Completions now work for inline long-option syntax like --flag=value: the fragment after = is used to narrow suggested values, the full --flag= prefix is reattached to each candidate (since shells replace the whole word), and file-path fallback still applies when a flag has no explicit choices. Fixes #​999.
  • (docs) Strip authored ANSI from plain help (#​1357, @​jdx). Style::PLAIN now removes ANSI CSI/SGR sequences that were already baked into command metadata (common when migrating from clap's color_print::cstr! help), keeping plain terminal help and generated Markdown escape-free while colored output is unchanged.
  • (help) Keep root help on the root page (#​1358, @​jdx). Before/after help, examples, author, and license are now command-local instead of falling back to the root spec. Root-specific material no longer appears on unrelated leaf commands (e.g. mise self-update --help), aligning with clap's command-local help behavior. Applied consistently across the Rust renderer, documentation templates, and the Go renderer.

New Contributors

Full Changelog: jdx/usage@v6.6.0...v6.6.1

💚 Sponsor usage

usage is built and maintained by @​jdx, an open source developer at entire.io, the title sponsor of his open source work.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider becoming an individual or company sponsor. Your support funds ongoing development and helps keep usage fast, free, and independent.

v6.6.0: : Scoped flags and implicit clauses

Compare Source

This small release extends the repeatable clause groups introduced in v6.5.0 with per-instance scoped flags and separator-free (implicit) clauses, and completes their integration across the compiled parser, portable KDL, help, completions, and generated documentation.

Added

  • Scoped flags and implicit clauses. Clauses can now carry flag nodes that are scoped to a single repeatable instance and reset at each boundary. The separator is now optional: when omitted, a clause with exactly one required, non-variadic positional ends each instance implicitly as soon as that terminal positional is consumed. Scoped flags precede and apply to the next terminal positional, and the parser rejects ambiguous implicit layouts, conflicting flag spellings, duplicate scalar flags within an instance, and trailing scoped flags that never complete an instance. Threaded through the interpreted parser, the compiled argv parser, Rust derive, portable KDL emission, help/completion, usage diff, and the generated Go bindings (#​1343, @​jdx). Requires min_usage_version "6.6".

    clause "tools" {
      flag "--postinstall <COMMAND>"
      arg "<tool>"
    }

    use --postinstall A a --postinstall B b produces two tools instances: postinstall="A", tool="a" and postinstall="B", tool="b". In Rust derive, omit separator and place the scoped fields on the nested Args type.

Fixed

  • Complete implicit clause integration (#​1345, @​jdx):
    • Command-level relationships (requires, conflicts, etc.) can now target arguments inside typed clauses in the compiled parser, so e.g. --force can require a clause's terminal positional.
    • Portable KDL now emits spec-facing argument names (e.g. TOOL, --postinstall) for clause relationship fields instead of Rust field selectors, keeping reference-parser round-trips valid.
    • Repeated clauses are now rendered as optional groups (wrapped in […]) in compiled help, manpage synopsis, and Markdown, and clause-scoped flags and arguments now appear in generated documentation. Empty clauses no longer fail to render.

Full Changelog: jdx/usage@v6.5.0...v6.6.0

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.5.0: : Sigils, clauses, and Cobra examples

Compare Source

This release introduces two new positional-argument primitives — sigil-classified arguments and repeatable clause groups — plus support for Cobra's Example field when generating specs, and a zsh completion fix for aliases.

Added

  • Sigil-classified positional arguments. Positionals can now be declared with a leading sigil prefix so they are matched by that prefix rather than by slot order. The prefix is treated as syntax and stripped before the value is stored, validated, or completed, and a sigil argument never advances the ordinary positional cursor — so classified values can interleave with flags and normal positionals. Completion, canonical KDL, argv tables, derive metadata, the Python/TypeScript SDKs, and the conformance corpus all carry sigils through the same contract, and tab completion strips/restores the prefix on every candidate (#​1322, #​1319, @​jdx). Requires min_usage_version "6.5".

    arg "[tool]..." sigil="+" {
      choices "node@22" "node@24" "python@3.14"
    }
    arg "<command>"
    arg "[args]..."

    With that spec, ex +node@24 node -v binds tool=["node@24"], command="node", and args=["-v"]. In Rust derive, annotate the field with #[usage(sigil = "+")].

  • Repeatable clause groups. A command can declare one separator-delimited group of positionals that repeats: each separator ends the current instance and starts a new one instead of overwriting it, and every instance is stored independently in parse output. Flag and positional state reset at each boundary, an explicit -- protects a literal separator, and completion treats the separator like a restart. Clauses are wired through the interpreted parser, the zero-allocation compiled argv parser, Rust derive (#[usage(clause, separator = "…")] on Vec<T>), the Go parser, and usage diff (which reports clause add/remove/separator changes as breaking) (#​1321, #​1320, @​jdx). Requires min_usage_version "6.6".

    clause "tasks" separator=":::" {
      arg "<task>"
      arg "[args]..." var=#true double_dash="automatic"
    }

    run lint --fix ::: test --all produces two tasks instances: task="lint", args=["--fix"] and task="test", args=["--all"].

  • Cobra Example field support. Specs generated with --usage-spec now include Cobra's Example text as example nodes — a root command's example becomes a top-level node, and a subcommand's becomes a child of its cmd block. The conventional two-space indent is stripped while multiline formatting and comment lines are preserved (#​1333, @​thecodesmith).

Fixed

  • (zsh) Command-position aliases are now expanded before the line is sent to the completion binary, so completions work for aliases that add arguments (e.g. gfin="mise run git:finish-branch"). Recursive and cyclic aliases are handled safely (#​1330, @​halms).

Changed

  • The Rust framework (usage-rs) documentation and site no longer carry the experimental label; usage-cli itself is built with it. The separate usage-dynamic crate remains marked experimental, and Go remains a work in progress (#​1334, @​jdx).

New Contributors

Full Changelog: jdx/usage@v6.4.1...v6.5.0

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.4.1: : Colorful Help and Sharper Negative-Value Parsing

Compare Source

A focused patch release that adds terminal-aware color to interpreted help output, tightens how negative numbers are parsed as flag values, and lowers the published crates' minimum supported Rust version.

Added

  • Colorized help output. The usage CLI, usage bash, and usage exec now render interpreted help with terminal-aware semantic styling (headings, options, metavars, inline markdown, and help_template {$…} tags). Coloring is auto-detected from the terminal and honors NO_COLOR and CLICOLOR_FORCE; plain rendering remains available for snapshots and generated artifacts (#​1309, @​jdx).

Fixed

  • More predictable negative-value parsing. Tokens like -1 are only consumed as a detached flag value when allow_negative_numbers is set or when the flag's value is truly required (no default_missing, not optional). This keeps optional and default_missing flags from swallowing negative numbers during subcommand and external_subcommand discovery, while required flags and explicit opt-ins still bind them correctly. Missing-value errors are also now reported for the awaiting flag even when another recognized option follows (#​1317, #​1318, @​jdx).
  • Hidden commands excluded from Markdown docs. Single-file Markdown reference generation no longer emits sections for commands marked hide=#true, matching the existing index and flag/arg filtering (#​1315, @​jdx).
  • Simplified the required_unless predicate logic for arguments and flags with no change in behavior (#​1326, @​jdx).

Changed

  • Lowered MSRV to Rust 1.91. The published usage-lib, usage-dynamic, clap_usage, and usage-cli crates now build on Rust 1.91 (down from 1.95), letting usage-cli install on runner images that ship Rust 1.94 (#​1314, @​jdx).

Dependency Updates

Full Changelog: jdx/usage@v6.4.0...v6.4.1

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.4.0: : XDG config layers and terminal-aware help wrapping

Compare Source

This release adds XDG-based config file resolution, teaches --help to wrap to the terminal width with a smarter column layout, fixes zsh completions at mid-line cursor positions, and slims down the library's dependency tree with an independent Markdown feature.

Added

  • XDG file layers for config resolution. FileLayer::xdg(XdgBase, path) resolves a relative path under the standard XDG config, data, state, cache, or runtime bases, honoring each base's defaults, absolute-path rules, and precedence with no new dependencies. Config and data bases include system search directories (with the user file winning), while state, cache, and runtime stay user-scoped. The Config derive gains matching #[usage(file(path = "…", xdg = "config"))] metadata that expands into the standard precedence chain in the emitted spec (#​1303, @​jdx).

    use usage::config::{FileLayer, XdgBase};
    
    // Reads $XDG_CONFIG_HOME then $XDG_CONFIG_DIRS in precedence order,
    // falling back to $HOME/.config and /etc/xdg when unset.
    let layer = FileLayer::xdg(XdgBase::Config, "ex/config.toml");

Fixed

  • Terminal help now wraps to the terminal width. Help output uses a hybrid column layout: long option spellings keep their description inline when at least 30 columns remain, otherwise the prose stacks under the shared description column. Paragraphs, section intros, annotations, bullet and numbered lists (with hanging indents), and labelled notes/warnings all wrap, while blank lines and preformatted (4-space/tab-indented) lines are preserved. The Rust reference renderer, the dependency-free usage-argv renderer, and the generated Go renderer stay in parity (#​1304, @​jdx).
  • zsh completions respect the cursor position. Generated zsh scripts now forward zsh's one-based CURRENT to complete-word as a zero-based --cword, so completing a word in the middle of a command line (for example --f before a trailing argument) resolves against the correct word instead of the last one (#​1300, @​jdx, fixes #​1298).

Changed

  • Independent markdown and manpage doc features. Markdown and manpage rendering are now separate features so consumers who only generate Markdown can drop the roff dependency. The existing docs and roff feature names remain as aliases. Internally, heck, shell-words, and strum were replaced with focused in-tree implementations and unicode-width was bumped to 0.2, shrinking the dependency footprint while keeping the public API and error variants stable (#​1301, @​jdx).

    usage-lib = { version = "6", default-features = false, features = ["markdown"] }

Full Changelog: jdx/usage@v6.3.0...v6.4.0

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.3.0: : Colorful help by default and a slimmer dependency tree

Compare Source

This release brings semantic colors to --help output by default, adds a runtime style vocabulary for help_template, tightens help-column layout, and removes the kdl and default miette dependencies from the library.

Added

  • Semantic colors in help output by default. Coloured --help now renders headings, option literals, and metavariables with distinct semantic colors so pages are easier to scan, while plain and piped output stays untouched (#​1297, @​jdx).

  • Runtime style tags in help_template. Templates can now colour and emphasize their own prose with a dependency-free tag vocabulary of 23 named styles (heading, option, metavar, the 8 standard and 8 bright ANSI colors, plus bold, dim, italic, underline). Styles nest and combine, {$$…}/{/$$} escape a literal tag, and substituted section text stays opaque so prose containing {$red} is left alone. Malformed markup falls back safely instead of panicking, and the vocabulary is validated in both Rust derives and KDL specs (#​1297, @​jdx).

    help_template = "{$heading}MY TOOL{/$}\n\n{{usage}}\n\n{$cyan}{{flags}}{/$}"
    
  • Optional miette feature. With the library's own error rendering now built in, an opt-in miette feature makes UsageErr and KDL parse diagnostics implement miette::Diagnostic again, preserving source spans, labels, severity, and help text for callers that already use a miette reporter (#​1296, @​jdx).

Fixed

  • Long entries no longer widen the whole help table. The aligned usage column is now capped at 40% of the remaining width, so a single long flag, argument, or command name (for example --report-unused-disable-directives-severity <SEVERITY>) no longer forces every entry on the page into block layout. Oversized entries drop into a wrapped block under their own spelling while shorter neighbors keep a readable two-column layout. Applied consistently across the reference, zero-allocation, and Go renderers (#​1293, @​jdx).
  • Repeatability ellipses removed from output. The marker is no longer appended to repeatable flags in help tables, Usage: synopses, Markdown, or generated SDK docs, so options render with ordinary spellings like --env <ENV>. Value-side ellipses (<arg>…) are unchanged, and repeatability is still preserved structurally in the spec via var (#​1295, @​jdx).
  • Go renderer now prints section prose. The Go help renderer honours the headings prose field introduced in v6.2.0, so a generated Go CLI renders the same declared section text as the Rust renderer instead of printing the heading alone (#​1290, @​jdx).

Changed

  • kdl and default miette dependencies removed. usage-lib now vendors a trimmed KDL v2 parser and renders diagnostics (source labels, help, and codes) with a small in-process renderer, dropping two dependencies from the default build without changing spec parsing behaviour. Apache-2.0 notices for the vendored code are recorded in NOTICE.md (#​1296, @​jdx).

Breaking Changes

  • UsageErr no longer derives miette::Diagnostic by default. Callers who relied on miette integration should enable the new miette feature to restore it (#​1296).
  • SpecFlag::usage() no longer round-trips the repeatability marker: parsing --flag… still sets var, but reprinting yields --flag. Keep var=#true as the source of truth in specs rather than relying on the suffix surviving a reparse (#​1295).

Full Changelog: jdx/usage@v6.2.0...v6.3.0

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.2.0: : Embedded parsing, richer specs, and a redesigned help page

Compare Source

Added

  • Embedded parse outcomes. embedded::outcome and the derive-generated Cli::embedded_outcome / embedded_outcome_into let N-API, WASM, editor, and test-runner hosts parse without terminating the process, returning a rendered Outcome::Exit with stream and clap-compatible status (#​1250, #​1270, #​1281).
  • Structured diagnostic reports. diagnostic::report returns a stable Code, subject, and optional ArgvSpan (index plus byte offsets into OsStr) so hosts can label parse failures without scraping terminal text (#​1255).
  • Opt-in response files. usage::response::expand pre-parses @file arguments with shell-style quoting, nested includes, @@ escaping, and cycle detection — kept off the zero-allocation parse path (#​1259).
  • Ordered argument groups. #[usage(multiple)] on an ArgGroup enum collects related flags like -A/-W/-D into Vec<T> in argv order (#​1271).
  • Value-carrying argument groups. ArgGroup tuple variants now declare one value-taking flag (Migrate(Source), StdinFilepath(PathBuf)), bound through FromStr, lossless path conversion, or ValueEnum (#​1253).
  • Typed command finalization. #[usage(validate_with = …)] runs command-wide invariants after field conversion, and #[usage(try_into = DomainType)] adds parse_into* entry points that finalize through TryFrom (#​1254).
  • Runtime-computed defaults. default_fn evaluates a typed default at parse time, with default_note for help prose that describes it honestly (#​1256).
  • Dynamic command catalogs. New usage-dynamic crate merges runtime-discovered plugin specs into a derived host's help, completion, and parsing via Catalog::builder, attaching to a static external_subcommand catch-all (#​1275).
  • Addressable help topics. help::topics and help::render_topic render a single standard or help_heading section without inventing fake subcommands (#​1257).
  • Inline formatting in help text. Coloured --help renders Markdown-style bold, italic, inline-code, and strikethrough spans in prose, leaving plain and piped output unchanged (#​1245).
  • Elvish shell completions. Elvish joins bash, zsh, fish, PowerShell, and Nushell as a first-class completion target (#​1243).
  • Semantic completion candidates. Candidates carry a kind (Command, Flag, File, Directory, Value) so PowerShell can use native CompletionResult types, plus a display label so zsh and PowerShell can show a richer name while inserting value (#​1239, #​1242).
  • Path extension filters. Specs declare type="path:toml,yaml" (or use .extensions("toml", "yaml") on FilePath/AnyPath) and every generated completion script filters accordingly; directories still traverse (#​1240).
  • Completion traces. Public CompletionTrace records words, prefix, command path, cursor owner, separator state, candidates, and shell path fallback for a Tab answer (#​1241).
  • Grouped help template sections. {{grouped_args}}, {{ungrouped_args}}, {{grouped_flags}}, and {{ungrouped_flags}} let templates interleave named help_heading groups with default lists (#​1251).
  • Section prose on headings. heading("Ignore Files", help = "…") (and heading "Title" help="…" in KDL) puts a sentence under a named section, next to the entries it explains (#​1282).
  • Command outputs, exit codes, and media types. Specs declare output blocks with text/JSON/JSONL framing, selectors, defaults, JSON Schemas (including schema file="…"), an optional media_type, and documented exit codes — surfaced through derives, MCP, generated Python/TypeScript SDKs, Markdown, and manpages (#​1249, #​1274).
  • Semantic note and warning blocks. #[usage(note = "…", warning = "…")] (or KDL note/warning children) render as labeled admonitions in long help and portable Markdown blockquotes (#​1273).
  • Surface availability metadata. #[usage(surface = "…", available_if(…))] carries descriptive audience labels through KDL, JSON, docs, and conformance tables without changing parse behavior (#​1258).
  • Overridable Markdown templates. MarkdownRenderer::with_template and the usage generate markdown --template NAME=PATH flag replace individual bundled Tera templates while unchanged ones remain available via {% include %} (#​1267).

Changed

  • Compact Markdown references by default. Generated Markdown now uses MarkdownTheme::Compact — dense grouped lists instead of one heading per argument or flag, with title-cased metadata labels, "Output Formats" instead of "Output", and long output catalogs collapsed behind <details>. The previous layout is MarkdownTheme::Detailed (#​1272, #​1280).
  • Redesigned command lists on -h and --help. Rows now show one aligned column of leaf names plus a short summary; usage syntax and children's full long_help stay on their own pages. mise's root --help drops from hundreds of lines to 136 (#​1284).
  • Short help wraps. Descriptions and annotations like [env: …] no longer run off the terminal on -h; they join first and wrap into the description column together, matching what --help has always done (#​1287).
  • Long-help annotations align to the description column. [possible values: …], (default: …), and env notes now sit under the description they qualify instead of at a fixed four-space indent (#​1291).

Fixed

  • Attached completion values. --format=j now completes as --format=json — static choices, named completers, and runtime overlays route through the attached-value context. Generated specs also materialize the parser-supplied help/version spellings as builtin=#true flags so listings and completions see them (#​1277).
  • Flattened command metadata. Outputs, select, and exit codes declared on flattened Args types survive spec emission (including nested flatten) (#​1268).
  • Typed defaults with restricted choices. Choice validation now runs only on values from argv or environment variables, so a default_fn may return an empty or non-advertised typed value (#​1269).
  • Override does not erase an invalid choice. mise --log-level=v --trace used to be accepted by usage-argv (and usage-go) because the post-binding choice check sat inside the given guard that overrides clears. Both parsers now judge a displaced flag's leftover choice like usage-lib and clap do; Go exports a matching CheckDisplaced (#​1286).
  • KDL writers agree on three more nodes. write_group quotes dashed members ("--allow" not --allow), cmd writes help_heading before help, and root before_help/after_help move earlier and into before-then-after order. A maximal fixture now covers every node both writers emit (#​1289).
  • Generated partial fields no longer trip Clippy. #[expect(clippy::pub_underscore_fields)] on Partial structs keeps internal fields public for cross-module flattening without noisy adopter lints (#​1278).
  • Nushell completion. Replaces deprecated str downcase usage on Windows so case-insensitive command matching keeps working (#​1262 by @​TheBearodactyl).

Performance

  • Skip empty admonition contexts in Markdown rendering, clawing back most of the cost added by note/warning blocks (#​1279).
  • Reduce sort code size in the argv hot path (#​1264).

New Contributors

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.1.1: : Windows path fixes and slimmer derived binaries

Compare Source

A patch release focused on making usage a good citizen on Windows and shrinking the code the derive macro generates. Five separator- and prefix-aware fixes across complete, config and argv land alongside two derive perf passes that trim ~16.5% off a mise-scale stripped binary.

Fixed

  • Path completion keeps the separator you typed. complete_path already accepted / or \ on Windows on the way in, but wrote back the platform separator for the middle of the path and a hard-coded / for the trailing directory marker, so typing target/de/inc came back as target\debug\incremental/ — a spelling no shell will match. Output now uses the same separator the token already contains (#​1230 by @​JamBalaya56562).
  • Config paths lose the verbatim prefix. normalize still canonicalizes for boundary checks, but strips the Windows \\?\ / UNC extended-length prefix before returning, so FileLayer::paths — which config explain reports as provenance — matches what a caller built with current_dir().join(…) (#​1232 by @​JamBalaya56562).
  • Install plans respect the target platform. plan takes a Platform for a reason: an install plan is made for a machine, not on one. Three places had regressed to using the host's separator (and Path::is_absolute / Path::ends_with in tests) — a Linux plan made on Windows was emitting fpath+=('/home/u\.local\share\zsh\site-functions'). All fixed to route through Platform::separator and the crate's own platform-aware helpers (#​1233 by @​JamBalaya56562).
  • Simpler completion-script headers. Rust and Go generators now emit a single @generated by … marker line instead of the extra "do not edit / no cached spec" preamble (#​1226 by @​jdx).
  • Cleaner flag reference docs. Generated Markdown headings show only the canonical short and long form; additional visible spellings move to a dedicated Aliases line. Hidden-alias filtering and interactive help are unchanged (#​1228 by @​jdx).

Performance

Two stacked derive-macro passes shrink the code every generated build() carries, without changing behavior or error messages:

  • Cold error construction moves out of line into four #[cold] #[inline(never)] builders in usage-argv (invalid_utf8_value, invalid_parsed_value, invalid_choice_value, invalid_os_value). On a mise-sized shadow binary this drops the stripped size from 1,579 KB to 1,369 KB (−210 KB, −13.3%) and roughly halves generated build() code. Cold parse instructions dip 0.9%; wall time is unchanged within noise (#​1235 by @​jdx).
  • Repeated-value collection loops are shared through four monomorphized helpers (utf8_values, parsed_values, os_values, spec::choice_values) with an inlined is_empty() fast path that avoids paying for a call when a Vec-shaped field received nothing. Another −51 KB on top, for a cumulative −261 KB (−16.5%) across the stack; instruction counts end up below the pre-stack baseline (#​1236 by @​jdx).

Tests

  • Joined Windows test paths component-by-component so a self-comparison stops disagreeing with itself, and scoped the "refuse to skip under CI" guard for zsh/fish/bash-completion to Unix — Git for Windows does not ship bash-completion, and the workflow does not install POSIX shells on Windows either (#​1229 by @​JamBalaya56562).
  • Silenced two Windows-only warnings (unused import: WarningKind, enum_variant_names on Shell::PowerShell) so cargo clippy --all-targets -- -D warnings passes there (#​1234 by @​JamBalaya56562).

Between them, these three test PRs take a windows-latest cargo test --all --all-features run from 2,383 pass / 5 fail to 2,393 pass / 0 fail, clearing the way for a real Windows CI job.

Full Changelog: jdx/usage@v6.1.0...v6.1.1

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.1.0: : Sharper derives, richer dispatch

Compare Source

This release sharpens the Rust derive framework introduced in 6.0: #[usage(run)] now handles the enum shapes real clap CLIs actually have, help and diagnostics respect the runtime identity of parse_from callers, and flatten-site help headings work. On the CLI itself, settings move to a prefix mise cannot strip, and generated KDL now round-trips multiline help.

Added

Broader #[usage(run)] dispatch (#​1221)

The derived dispatch previously required every variant to wrap a named Args type, the whole enum to be sync or async, and the root to hold nothing but its subcommand field. That is now covered:

  • Unit and inline variants get a generated {Enum}{Variant} struct you can impl Run on.
  • Mixed sync/async: put #[usage(run_async)] on the enum and #[usage(run)] on the variant that should not .await.
  • Catch-alls: #[usage(run, external = fallback)] forwards the unmatched argv (and context, if run_with).
  • Roots with flags: #[usage(run)] on a struct with --verbose and a required subcommand generates run_command instead of impl Run, so top-level flags are not dropped.
  • Skip context: #[usage(no_ctx)] plus run_with_lazy / run_async_with_lazy (FnOnce() -> Ctx) lets commands like version avoid loading a config file.
  • output = Type explicitly names the match's Output instead of borrowing it from the first command.
Runtime identity in help, and flatten-site headings (#​1220)

parse() already overlays the embedder's computed name / bin. parse_from callers that rendered help through Cli::spec() did not. Cli::render_help and Cli::render_failure now apply the same identity, so vendored parsers stop leaking the portable aube name into help and diagnostics.

#[usage(flatten, next_help_heading = "…")] at the flatten site now groups the unheaded flags of a flattened Args struct — matching clap's behavior — and reaches into subcommand help and generated KDL too.

USAGECLI_* settings prefix (#​1213 by @​JamBalaya56562)

Because Windows env-var names are case-insensitive, USAGE_DEBUG (a usage-cli setting) collides with usage_debug (a spec's own flag), and mise clears everything starting with usage_ before running a task — including usage-cli's settings. Settings can now be read under USAGECLI_*:

New Legacy (still read)
USAGECLI_SHELL_{BASH,ZSH,FISH,PWSH} USAGE_SHELL_*
USAGECLI_DEBUG USAGE_DEBUG
USAGECLI_TRACE USAGE_TRACE
USAGECLI_LOG USAGE_LOG

First name set wins. As a side benefit, USAGE_LOG is no longer written back into the environment with set_var, so a spawned script's own log argument survives.

Fixed

  • Long help flows like short help. Non-verbatim doc comments wrap the same way for long_help as for help: source-wrapped lines become spaces, indented examples and fenced code blocks keep their breaks, and verbatim_doc_comment is untouched (#​1215).
  • KDL keeps newlines. Spec::to_kdl emits #"""…"""# raw multiline strings for values that contain newlines, so generated .usage.kdl no longer collapses multi-paragraph help into one giant escaped line (#​1215).

Changed

  • Removed clap-compatible attribute spellings (a989d26b). Derives now accept only #[usage(...)]. #[command(...)], #[arg(...)], #[value(...)], #[group(...)], and inner synonyms (id, default_value, conflicts_with, value_parser, last, …) still parse, but fail at the source span with a diagnostic telling you the native replacement. Implicit clap-style #[group(...)] generation for one-member groups is gone — requiredness comes from the field type or required.
  • Stricter variant validation (#​1224): redundant #[usage(run_async)] on an enum variant is now rejected while parsing the attribute.

Documentation

  • Complete KDL reference for the spec (#​1214).
  • Rust framework docs refreshed: sharper framework page (#​1222), summarized parser performance page (#​1219), combined clap migration guide (#​1217), refreshed clap binary-size comparison (#​1212), dropped a restated intro line (#​1211).
  • Benchmark charts added to the Rust and Go pages and comparison methodology clarified (#​1209, #​1210).

Breaking Changes

  • Derive attributes must use #[usage(...)]. Any remaining clap-shaped attributes (#[command], #[arg], #[value], #[group], or their inner synonyms) will now fail to compile with a diagnostic pointing at the replacement. See the clap migration guide for before/after rewrites.
  • Implicit single-member #[group(...)] generation is gone. If you relied on it for requiredness, mark the field required or use its type (e.g. non-Option) instead.

Full Changelog: jdx/usage@v6.0.0...v6.1.0

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v6.0.0

Compare Source

Usage 6.0

Usage 6 is a much larger release than its version number can comfortably summarize. Since 5.1, the project has grown from a spec parser and artifact generator into a complete CLI platform: the new usage-rs reference framework for Rust, the beginnings of the usage-go reference framework, layered configuration, portable validation, richer completions, compatibility tooling, and a substantially more expressive Usage spec.

The idea is still the same: a CLI should have one machine-readable contract. In 6.0, that contract can now drive the program itself as well as its help, completions, docs, manpages, config schema, and compatibility checks.

Introducing usage-rs

usage-rs is the new reference framework for building Rust CLIs with Usage. Declare typed commands, arguments, subcommands, value enums, argument groups, and settings with ordinary structs and enums; usage-rs compiles the declaration into static data instead of constructing a command tree at startup.

That gives applications:

  • Typed parsing with no runtime parser construction
  • Built-in -h, --help, help, --version, clap-shaped diagnostics, and suggestions
  • Generated sync/async command dispatch and update_from support
  • Shell completion scripts and in-process dynamic completers
  • A built-in __usage_spec__ endpoint, so the running binary can describe itself
  • First-party assertions for parsing, help, execution, and completion behavior

On the checked-in mise-scale benchmark—211 commands, 711 flags, and 128 positionals—the parse-only path takes about 7,377 instructions / 0.7 µs, with no allocations when no owned values are bound. See the methodology and current numbers.

usage-rs is experimental: it is complete enough that usage-cli now uses it itself, but 6.x point releases may still change APIs.

Configuration becomes part of the contract

usage-rs can resolve settings across command-line, environment, and file layers while retaining provenance for every value. Its Config derive generates the registry, typed reader, and portable spec metadata from the same settings struct.

The resolver supports typed values, merge policies, aliases and renames, deprecation milestones, TOML/JSON/YAML readers, lossy reads, and explanations of where a value came from. Because config declarations live in the spec, the CLI can also generate JSON Schema and complete config keys and values.

See the configuration guide.

A substantially richer spec and CLI

The spec now covers much more of a real CLI's behavior: conflicts, requirements, overrides, groups, reusable flag sets, value-conditional rules, fixed and variadic arity, external and default subcommands, token-boundary controls, deprecations, portable expression validation, config metadata, help layout, and command effects.

Two new commands make that contract easier to operate:

  • usage explain shows how argv was interpreted, including token roles, fallbacks, provenance, warnings, and accumulated errors.
  • usage diff compares two specs and classifies changes as breaking, compatible, or metadata-only. It has machine-readable output and CI-friendly exit behavior.

Completion generation gained richer value hints, config completion, shell-safe quoting, partial-path expansion, aliases, async overlays, and --install for placing scripts where each shell expects them. JSON Schema generation for CLI config is new as well.

Introducing usage-go

usage-go is the new Go reference framework. It follows the same static-data design, generates typed command structs from a Usage spec, and keeps parsing, validation metadata, and help text linker-separable.

This work is not ready for adoption or testing yet. Its APIs and generated output are still in flux, and the published documentation is a preview of the direction rather than a stability promise.

Breaking changes and migration notes

  • usage-rs and usage-go should be treated as brand-new in 6.0. Some implementation crates were accidentally published with 5.x versions, but those releases did not constitute supported public frameworks or an API lineage to migrate from. Start with the 6.0 framework documentation.
  • UsageErr is now #[non_exhaustive], and file/shell failures have dedicated variants. Downstream exhaustive matches need a fallback arm.
  • subcommand_required is now enforced by the reference parser. An invocation that previously slipped through without a required child command now fails as declared.
  • Rust flatten declarations are emitted as reusable flagset / use nodes instead of duplicating flags under every command. The accepted command line is unchanged, but tools comparing serialized generated specs will see a structural change.
  • Usage no longer vendors or embeds bash-completion. --include-bash-completion-lib and the corresponding Rust option were removed. Generated Bash scripts require bash-completion 2.11 or newer to be installed and sourced; the scripts now diagnose a missing library clearly.
  • Dependency and feature cleanup removed unused transitive crates and stopped implicitly enabling capabilities for consumers. Direct usage-lib users should declare the features they actually use.

For clap adopters, the usage-rs migration guide documents the mechanical derive mapping, known compatibility gaps, and intentional boundaries around runtime builders and ArgMatches.

Everything else

This release spans 347 commits and 500 changed files. The curated notes above are the practical overview; the full changelog retains every feature, fix, performance change, and pull request, and the complete comparison is available on GitHub.

v5.1.0: : Embed specs from strings, cleaner include metadata

Compare Source

A small feature release: embedders get a string-based script parser, included specs stop clobbering their parent's inferred metadata, and the test suite finally runs cleanly on Windows.

Added

  • Parse embedded USAGE comments from a string (#​782 by @​jdx). The new Spec::parse_script_str lets embedders turn a script body into a Spec without writing to a temp file or hand-deserializing KDL:

    let spec = Spec::parse_script_str(r#"
    #!/bin/bash
    #USAGE bin "mycli"
    #USAGE flag "--foo" help="a flag"
    "#)?;

    Because there's no source path, bin/name are not inferred from a filename and relative include paths are rejected with relative includes require a source file; absolute includes still work. The file-based parse_script now shares the same internal path, so behavior stays consistent.

Fixed

  • Included specs no longer overwrite parent metadata (#​786 by @​jdx). parse_file derives a missing bin (and then name) from the filename — but include was going through the same path, so an empty included fragment would take on its own filename and overwrite the parent spec, producing a spurious missing-cmd-help. Filename-based inference is now limited to the top-level spec; explicit metadata in includes still merges as before. The unreachable missing-name lint (which fired for stdin but never for files) was also removed so file and stdin linting behave the same way. Closes #​784 and #​785.

Changed

  • Corrected USAGE comment marker documentation (#​782). The docs previously described # USAGE: and // USAGE:; the real supported markers are #USAGE, //USAGE, ::USAGE, and their [USAGE] variants.
  • Bumped rmcp to v3 (#​780 by @​renovate). Tracks the MCP 2026-07-28 protocol revision.

Tests

  • Windows test suite is fully green (#​771 by @​JamBalaya56562). Reworks the shell skip guards to probe the actual precondition instead of a proxy (WSL's bash.exe cheerfully answers --version and then fails everything else), routes fixture invocations through USAGE_SHELL_<SHELL>, normalizes paths handed to shell script bodies and $PATH, and removes the #![cfg(unix)] gate on shell_override.rs — which held back the very tests for the Windows-facing USAGE_SHELL_<SHELL> feature added in v5.0.0. Result on a windows-latest runner: 538 passed, 0 skipped. No library or CLI source is touched.

Full Changelog: jdx/usage@v5.0.0...v5.1.0

💚 Sponsor usage

usage is maintained by @​jdx, an open source developer for entire.io, the title sponsor of the jdx.dev open source tools including mise, aube, hk, and more. Work on usage is funded by sponsorships.

If usage powers CLI specs, docs, or completions for a tool you maintain or use, please consider sponsoring at jdx.dev. Every sponsorship helps the project stay independent and moving.

v5.0.0: : Double-dash routing and Windows shell fixes

Compare Source

A parser-level fix that makes double_dash="required" actually behave as declared drives the major bump: values before -- are now rejected, and values after -- are routed past greedy variadics to the arg that was waiting for them. The release also fixes a cluster of long-standing Windows problems — usage bash losing every usage_* variable under WSL,

Note

PR body was truncated to here.


Configuration

📅 Schedule: (UTC)

  • Branch creation
    • At any time (no schedule defined)
  • Automerge
    • At any time (no schedule defined)

🚦 Automerge: Disabled by config. Please merge this manually once you are satisfied.

Rebasing: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 Ignore: Close this PR and you won't be reminded about this update again.


  • If you want to rebase/retry this PR, check this box

This PR was generated by Mend Renovate. View the repository job log.

@renovate
renovate Bot force-pushed the renovate/jdx-usage-6.x branch 8 times, most recently from ef0977c to 7d6ea33 Compare August 28, 2026 20:33
@renovate
renovate Bot force-pushed the renovate/jdx-usage-6.x branch 3 times, most recently from bcf7f27 to 41ecf3f Compare September 1, 2026 17:36
@renovate
renovate Bot force-pushed the renovate/jdx-usage-6.x branch from 41ecf3f to 15b04eb Compare September 2, 2026 00:00
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

0 participants