mirror of
https://github.com/storytold/designcraft.git
synced 2026-10-30 13:16:56 -06:00
Merge #254: fix(cli): --help prints usage to stdout and exits 0
Conflict: apps/designcraft-cli/src/main.rs: #254's USAGE const and usage_footer(); #127's '(--page, --scale and --pdf-options apply to the exports that follow them)' line moved into USAGE
This commit is contained in:
@@ -34,6 +34,19 @@ mod perf;
|
||||
use designcraft_engine::Session;
|
||||
use serde_json::{Value, json};
|
||||
|
||||
/// The usage block. Shared by `--help` (stdout, success) and an unknown command (stderr, failure).
|
||||
const USAGE: &str = "usage: designcraft-cli run [--in FILE | --sample] [--cmd ID[=JSON]]... [--page N] [--scale S] [--pdf-options JSON] [--export OUT] [--all-pages DIR]\n (--page, --scale and --pdf-options apply to the exports that follow them)\n designcraft-cli commands [FILTER]\n designcraft-cli describe COMMAND\n designcraft-cli script [FILE|-] [--in FILE | --sample] [--connect PORT] [--save OUT] [--export OUT] [--keep-going]\n designcraft-cli app [--port PORT] COMMAND [JSON] | --method METHOD [JSON]\n designcraft-cli mcp [--connect PORT] [--sample]\n designcraft-cli perf [--pages N] [--runs N] [--strict]\n designcraft-cli bench FILE [--runs N]\n designcraft-cli links\n designcraft-cli --version";
|
||||
|
||||
/// The links line under the usage block.
|
||||
fn usage_footer() -> String {
|
||||
format!(
|
||||
"\nCommunity: {} · {} · {}",
|
||||
designcraft_engine::links::DISCORD,
|
||||
designcraft_engine::links::APP_PAGE,
|
||||
designcraft_engine::links::GITHUB
|
||||
)
|
||||
}
|
||||
|
||||
/// stdout went away. A reader that stopped early (a closed pipe) ends the program quietly, as
|
||||
/// ripgrep does; any other write error is reported.
|
||||
fn stdout_failed(e: std::io::Error) -> ! {
|
||||
@@ -76,16 +89,16 @@ fn main() -> ExitCode {
|
||||
outln!("Discord {DISCORD}\nWebsite {WEBSITE}\nApp page {APP_PAGE}\nGitHub {GITHUB}\nIssues {ISSUES}");
|
||||
ExitCode::SUCCESS
|
||||
}
|
||||
// Asking for help is not an error: it goes to stdout and succeeds. An unknown command
|
||||
// still prints the same usage to stderr and fails.
|
||||
Some("--help" | "-h" | "help") => {
|
||||
outln!("{USAGE}");
|
||||
outln!("{}", usage_footer());
|
||||
ExitCode::SUCCESS
|
||||
}
|
||||
_ => {
|
||||
eprintln!(
|
||||
"usage: designcraft-cli run [--in FILE | --sample] [--cmd ID[=JSON]]... [--page N] [--scale S] [--pdf-options JSON] [--export OUT] [--all-pages DIR]\n (--page, --scale and --pdf-options apply to the exports that follow them)\n designcraft-cli commands [FILTER]\n designcraft-cli describe COMMAND\n designcraft-cli script [FILE|-] [--in FILE | --sample] [--connect PORT] [--save OUT] [--export OUT] [--keep-going]\n designcraft-cli app [--port PORT] COMMAND [JSON] | --method METHOD [JSON]\n designcraft-cli mcp [--connect PORT] [--sample]\n designcraft-cli perf [--pages N] [--runs N] [--strict]\n designcraft-cli bench FILE [--runs N]\n designcraft-cli links\n designcraft-cli --version"
|
||||
);
|
||||
eprintln!(
|
||||
"\nCommunity: {} · {} · {}",
|
||||
designcraft_engine::links::DISCORD,
|
||||
designcraft_engine::links::APP_PAGE,
|
||||
designcraft_engine::links::GITHUB
|
||||
);
|
||||
eprintln!("{USAGE}");
|
||||
eprintln!("{}", usage_footer());
|
||||
ExitCode::FAILURE
|
||||
}
|
||||
}
|
||||
|
||||
@@ -67,6 +67,26 @@ fn run_cmd_references_and_describe() {
|
||||
assert!(v.as_array().unwrap().iter().all(|c| c.to_string().contains("footnote")));
|
||||
}
|
||||
|
||||
/// `designcraft-cli --help` printed usage to stderr and exited 1; asking for help is not an
|
||||
/// error (#243). It now goes to stdout and succeeds, while an unknown command keeps the same
|
||||
/// usage on stderr and fails.
|
||||
#[test]
|
||||
fn help_goes_to_stdout_and_unknown_args_to_stderr() {
|
||||
for flag in ["--help", "-h", "help"] {
|
||||
let out = cli().arg(flag).output().unwrap();
|
||||
let stdout = String::from_utf8_lossy(&out.stdout);
|
||||
assert!(out.status.success(), "{flag}: {:?}", out.status);
|
||||
assert!(stdout.starts_with("usage: designcraft-cli"), "{flag}: {stdout:?}");
|
||||
assert!(stdout.contains("designcraft-cli --version"), "{flag}: {stdout:?}");
|
||||
assert!(out.stderr.is_empty(), "{flag} wrote to stderr: {}", String::from_utf8_lossy(&out.stderr));
|
||||
}
|
||||
// An unknown option is still an error: usage on stderr, nothing on stdout, non-zero exit.
|
||||
let out = cli().arg("--no-such-option").output().unwrap();
|
||||
assert!(!out.status.success(), "{:?}", out.status);
|
||||
assert!(out.stdout.is_empty(), "unexpected stdout: {}", String::from_utf8_lossy(&out.stdout));
|
||||
assert!(String::from_utf8_lossy(&out.stderr).starts_with("usage: designcraft-cli"));
|
||||
}
|
||||
|
||||
/// `designcraft-cli commands | head -1` panicked with "failed printing to
|
||||
/// stdout: Broken pipe (os error 32)" and exit status 101.
|
||||
#[test]
|
||||
|
||||
Reference in New Issue
Block a user