Introduces a static-binary build and Debian package (amd64/arm64) with version/commit/date stamped via -ldflags. Ships section-1 manpages for ctool, ctfetch, and ctail. Adds a `version` subcommand reachable as `ctool version`, `ctool -version`, `ctool --version`, `ctool fetch version`, `ctool tail version`, and via the ctfetch/ctail symlinks. Adds tests covering the dispatcher, fetch/tail argument parsing, and the formatter/helper functions. Adds a retrofit design document modelled on the vpp-maglev one, with FRs and NFRs for each tool and the dispatcher. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
125 lines
2.9 KiB
Groff
125 lines
2.9 KiB
Groff
.TH CTAIL 1 "April 2026" "ctool" "User Commands"
|
|
.SH NAME
|
|
ctail \- tail a Static CT log, printing one line per new entry
|
|
.SH SYNOPSIS
|
|
.B ctail
|
|
[\fIflags\fR] \fIlog\-url\fR
|
|
.PP
|
|
.B ctail version
|
|
.SH DESCRIPTION
|
|
.B ctail
|
|
polls a Static CT API log (c2sp.org/static\-ct\-api) and prints a
|
|
one\-liner to stdout for every certificate or precertificate that
|
|
appears in a newly\-completed data tile.
|
|
It is also available as the
|
|
.B tail
|
|
subcommand of
|
|
.BR ctool (1);
|
|
the two invocations are equivalent.
|
|
.PP
|
|
Status messages (startup banner, HTTP errors, progress complaints) go
|
|
to stderr; only the per\-entry one\-liners go to stdout, so the
|
|
output is safe to pipe into
|
|
.BR grep ,
|
|
.BR awk ,
|
|
or a log collector without mixing the two streams.
|
|
.SH OUTPUT FORMAT
|
|
One line per log entry, fixed\-width columns separated by spaces:
|
|
.PP
|
|
.RS
|
|
.EX
|
|
<leaf-index> <type> <validity-range> <issuer> <subject>
|
|
.EE
|
|
.RE
|
|
.TP
|
|
.B leaf\-index
|
|
Decimal index of the entry within the log's Merkle tree.
|
|
.TP
|
|
.B type
|
|
.B cert
|
|
for a final certificate,
|
|
.B pre
|
|
for a precertificate.
|
|
.TP
|
|
.B validity\-range
|
|
.IR YYYY\-MM\-DD .. YYYY\-MM\-DD ,
|
|
taken from the certificate's
|
|
.I NotBefore
|
|
and
|
|
.I NotAfter
|
|
fields.
|
|
.TP
|
|
.B issuer
|
|
Issuer common name, prefixed with the issuer organisation when the
|
|
CN alone is terse (so
|
|
.I R13
|
|
is shown as
|
|
.IR "Let's Encrypt R13" );
|
|
truncated to 40 characters with a trailing ellipsis if necessary.
|
|
.TP
|
|
.B subject
|
|
First DNS Subject Alternative Name, falling back to the certificate's
|
|
subject common name. Shown as
|
|
.I (unknown)
|
|
when neither is populated.
|
|
.SH FLAGS
|
|
.TP
|
|
.BI \-\-interval " duration"
|
|
How often to poll the log's
|
|
.B /checkpoint
|
|
endpoint. Minimum
|
|
.IR 1s ;
|
|
default
|
|
.IR 15s .
|
|
The interval timer starts when the checkpoint is fetched, so time
|
|
spent fetching the ensuing data tiles counts against the interval
|
|
and the next poll stays on schedule.
|
|
.TP
|
|
.BI \-\-from\-leaf " n"
|
|
Start at leaf index
|
|
.IR n .
|
|
The default,
|
|
.IR \-1 ,
|
|
means "start at the current tree tip" \(em no backfill.
|
|
.TP
|
|
.BI \-\-rate\-limit " duration"
|
|
Minimum time between outgoing HTTP requests to the log. Minimum
|
|
.IR 100ms ;
|
|
default
|
|
.IR 2s .
|
|
Lets the client stay a polite distance below any per\-IP rate limit
|
|
the log operator enforces.
|
|
.TP
|
|
.BI \-\-user\-agent " string"
|
|
User\-Agent header sent with every request. Default:
|
|
\fIctail/VERSION (https://git.ipng.ch/certificate\-transparency/)\fR.
|
|
.SH SUBCOMMANDS
|
|
.TP
|
|
.B version
|
|
Print the binary's version, git commit hash, and build date, then
|
|
exit.
|
|
.SH EXAMPLES
|
|
Follow a log from the current tip:
|
|
.PP
|
|
.RS
|
|
.EX
|
|
$ ctail https://halloumi2026h2.mon.ct.ipng.ch
|
|
.EE
|
|
.RE
|
|
.PP
|
|
Replay a log from the very first entry, polling every ten seconds:
|
|
.PP
|
|
.RS
|
|
.EX
|
|
$ ctail \-\-from\-leaf 0 \-\-interval 10s https://halloumi2026h2.mon.ct.ipng.ch
|
|
.EE
|
|
.RE
|
|
.SH NOTES
|
|
A data tile is only fetched once the checkpoint confirms it is
|
|
complete (256 entries). This avoids unnecessary 404s at the tree tip.
|
|
.SH SEE ALSO
|
|
.BR ctool (1),
|
|
.BR ctfetch (1)
|
|
.SH AUTHOR
|
|
Pim van Pelt <pim@ipng.ch>
|