summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJustus Winter <justus@sequoia-pgp.org>2021-01-19 11:22:31 +0100
committerJustus Winter <justus@sequoia-pgp.org>2021-01-19 12:19:47 +0100
commitc4f55892fc75a5c23abe97e5acf42c6a14f5574a (patch)
treec558aef797e274fec6881c98f27f29cdec108f4d
parent0f63b13d655cea6d7739150ddfa1b118f3c3f33f (diff)
sq: Generate usage documentation in build script.
- Unfortunately, we still need to commit the result. Once the external doc feature is merged, we can avoid this. See https://github.com/rust-lang/rust/issues/44732.
-rw-r--r--.gitlab-ci.yml3
-rw-r--r--sq/Makefile9
-rw-r--r--sq/build.rs78
-rw-r--r--sq/make-usage.sh54
-rw-r--r--sq/src/sq-usage.rs22
-rw-r--r--sq/src/sq_cli.rs4
6 files changed, 88 insertions, 82 deletions
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index ea7db163..2c7038a4 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -28,8 +28,7 @@ bullseye:
- cargo test --all --exclude sequoia-openpgp-ffi
- make
- if ! git diff --quiet Cargo.lock ; then echo "Cargo.lock changed. Please add the change to the corresponding commit." ; false ; fi
- - make -C sq update-usage
- - if ! git diff --quiet sq ; then echo "Please run 'make -C sq update-usage' and commit the result." ; false ; fi
+ - if ! git diff --quiet sq ; then echo "Please commit the changes to sq/src/sq-usage.rs." ; false ; fi
- make -C sqv update-usage
- if ! git diff --quiet sqv ; then echo "Please run 'make -C sqv update-usage' and commit the result." ; false ; fi
- if ! git diff --quiet ; then echo "The build changed the source. Please investigate." ; git diff ; fi
diff --git a/sq/Makefile b/sq/Makefile
index 74a0c512..d3fd4fc7 100644
--- a/sq/Makefile
+++ b/sq/Makefile
@@ -13,8 +13,6 @@ else
INSTALL ?= install
endif
-all: src/sq-usage.rs
-
# Installation.
.PHONY: build-release
build-release:
@@ -36,10 +34,3 @@ install: build-release
$(INSTALL) -t $(DESTDIR)$(PREFIX)/share/fish/completions \
$(CARGO_TARGET_DIR)/sq.fish
$(MAKE) -C../store install
-
-# Maintenance.
-.PHONY: update-usage
-update-usage: src/sq-usage.rs
-
-src/sq-usage.rs: make-usage.sh $(SQ)
- sh make-usage.sh $(SQ) >$@~ && mv $@~ $@
diff --git a/sq/build.rs b/sq/build.rs
index b7d3147d..25a9af8d 100644
--- a/sq/build.rs
+++ b/sq/build.rs
@@ -1,7 +1,6 @@
-use clap;
-
use std::env;
use std::fs;
+use std::io::{self, Write};
use clap::Shell;
mod sq_cli {
@@ -9,6 +8,19 @@ mod sq_cli {
}
fn main() {
+ println!("cargo:rerun-if-changed=build.rs");
+
+ // XXX: Revisit once
+ // https://github.com/rust-lang/rust/issues/44732 is stabilized.
+
+ let mut sq = sq_cli::build();
+ let mut main = fs::File::create("src/sq-usage.rs").unwrap();
+ dump_help(&mut main,
+ &mut sq,
+ vec![],
+ "#").unwrap();
+ writeln!(main, "\ninclude!(\"sq.rs\");").unwrap();
+
let outdir = match env::var_os("CARGO_TARGET_DIR") {
None => return,
Some(outdir) => outdir,
@@ -20,3 +32,65 @@ fn main() {
sq.gen_completions("sq", *shell, &outdir);
}
}
+
+fn dump_help(sink: &mut dyn io::Write,
+ sq: &mut clap::App,
+ cmd: Vec<String>,
+ heading: &str)
+ -> io::Result<()>
+{
+
+ if cmd.is_empty() {
+ writeln!(sink, "//! A command-line frontend for Sequoia.")?;
+ writeln!(sink, "//!")?;
+ writeln!(sink, "//! # Usage")?;
+ } else {
+ writeln!(sink, "//!")?;
+ writeln!(sink, "//! {} Subcommand {}", heading, cmd.join(" "))?;
+ }
+
+ writeln!(sink, "//!")?;
+
+ let args = std::iter::once("sq")
+ .chain(cmd.iter().map(|s| s.as_str()))
+ .chain(std::iter::once("--help"))
+ .collect::<Vec<_>>();
+
+ let help = sq.get_matches_from_safe_borrow(&args)
+ .unwrap_err().to_string();
+
+ writeln!(sink, "//! ```text")?;
+ for line in help.trim_end().split("\n").skip(1) {
+ if line == "" {
+ writeln!(sink, "//!")?;
+ } else {
+ writeln!(sink, "//! {}", line.trim_end())?;
+ }
+ }
+ writeln!(sink, "//! ```")?;
+
+ // Recurse.
+ let mut found_subcommands = false;
+ for subcmd in help.split("\n").filter_map(move |line| {
+ if line == "SUBCOMMANDS:" {
+ found_subcommands = true;
+ None
+ } else if found_subcommands {
+ if line.chars().nth(4).map(|c| ! c.is_ascii_whitespace())
+ .unwrap_or(false)
+ {
+ line.trim_start().split(" ").nth(0)
+ } else {
+ None
+ }
+ } else {
+ None
+ }
+ }).filter(|subcmd| *subcmd != "help") {
+ let mut c = cmd.clone();
+ c.push(subcmd.into());
+ dump_help(sink, sq, c, &format!("{}#", heading))?;
+ }
+
+ Ok(())
+}
diff --git a/sq/make-usage.sh b/sq/make-usage.sh
deleted file mode 100644
index 7bcbfcf2..00000000
--- a/sq/make-usage.sh
+++ /dev/null
@@ -1,54 +0,0 @@
-#!/bin/sh
-
-tool=$1
-
-quote() {
- sed 's@^@//! @' | sed 's/ $//'
-}
-
-begin_code() {
- printf '```text\n'
-}
-
-end_code() {
- printf '```\n'
-}
-
-dump_help() { # subcommand, indentation
- if [ -z "$1" ]
- then
- printf "\n# Usage\n\n"
- set "" "#"
- else
- printf "\n$2 Subcommand$1\n\n"
- fi
-
- help="`$tool $1 --help`"
-
- begin_code
- printf "$help\n" | tail -n +2
- end_code
-
- if echo $help | fgrep -q SUBCOMMANDS
- then
- printf "$help\n" |
- sed -n '/^SUBCOMMANDS:/,$p' |
- tail -n+2 |
- grep '^ [^ ]' |
- while read subcommand desc
- do
- if [ "$subcommand" = help ]; then
- continue
- fi
-
- dump_help "$1 $subcommand" "#$2"
- done
- fi
-}
-
-(
- printf "A command-line frontend for Sequoia.\n"
- dump_help
-) | quote
-
-printf '\ninclude!("'"$(basename $tool)"'.rs");\n'
diff --git a/sq/src/sq-usage.rs b/sq/src/sq-usage.rs
index 808d01bd..761b7aab 100644
--- a/sq/src/sq-usage.rs
+++ b/sq/src/sq-usage.rs
@@ -294,10 +294,10 @@
//! sq certring <SUBCOMMAND>
//!
//! FLAGS:
-//! -h, --help
+//! -h, --help
//! Prints help information
//!
-//! -V, --version
+//! -V, --version
//! Prints version information
//!
//!
@@ -319,35 +319,35 @@
//! sq certring filter [FLAGS] [OPTIONS] [--] [FILE]...
//!
//! FLAGS:
-//! -B, --binary
+//! -B, --binary
//! Don't ASCII-armor the certring
//!
-//! -h, --help
+//! -h, --help
//! Prints help information
//!
-//! -P, --prune-certs
+//! -P, --prune-certs
//! Remove certificate components not matching the filter
//!
-//! -V, --version
+//! -V, --version
//! Prints version information
//!
//!
//! OPTIONS:
-//! --domain <FQDN>...
+//! --domain <FQDN>...
//! Match on this email domain name
//!
-//! --email <ADDRESS>...
+//! --email <ADDRESS>...
//! Match on this email address
//!
-//! --name <NAME>...
+//! --name <NAME>...
//! Match on this name
//!
-//! -o, --output <FILE>
+//! -o, --output <FILE>
//! Sets the output file to use
//!
//!
//! ARGS:
-//! <FILE>...
+//! <FILE>...
//! Sets the input files to use
//! ```
//!
diff --git a/sq/src/sq_cli.rs b/sq/src/sq_cli.rs
index 814cde8d..d2c527ef 100644
--- a/sq/src/sq_cli.rs
+++ b/sq/src/sq_cli.rs
@@ -1,8 +1,4 @@
/// Command-line parser for sq.
-///
-/// If you change this file, please rebuild `sq`, run `make -C tool
-/// update-usage`, and commit the resulting changes to
-/// `sq/src/sq-usage.rs`.
use clap::{App, Arg, ArgGroup, SubCommand, AppSettings};