Skip to main content

ralph/commands/
cli_spec.rs

1//! CLI spec command implementation (wired into the hidden/internal `ralph __cli-spec` command).
2//!
3//! Responsibilities:
4//! - Provide a small "command layer" entrypoint that produces the deterministic CLI spec JSON for
5//!   the current build of Ralph.
6//! - Keep the execution/IO boundary separate from clap introspection and contract modeling.
7//!
8//! Not handled here:
9//! - Registering a user-facing `ralph cli-spec` (or similar) top-level command in clap.
10//! - Reading/writing files or printing to stdout/stderr.
11//!
12//! Invariants/assumptions:
13//! - Uses `Cli::command()` as the canonical source of the clap command tree.
14//! - Output must be deterministic across invocations within the same build.
15
16use anyhow::Result;
17
18use clap::CommandFactory;
19
20use crate::contracts::CliSpec;
21
22/// Build the structured `CliSpec` for the current Ralph CLI.
23pub fn build_cli_spec() -> CliSpec {
24    let command = crate::cli::Cli::command();
25    crate::cli_spec::cli_spec_from_command(&command)
26}
27
28/// Emit deterministic pretty JSON for the current Ralph CLI.
29pub fn emit_cli_spec_json_pretty() -> Result<String> {
30    let command = crate::cli::Cli::command();
31    crate::cli_spec::cli_spec_json_pretty_from_command(&command)
32}