Usability evidence, on the record.
Testimony captures manual test sessions the way usability research does it — a screen recording plus concurrent think-aloud narration — and turns them into machine-readable, time-aligned records: a word-timestamped transcript merged with a timestamped interaction stream, rendered as a report that shows what was said next to what was done.
voice ──► local Whisper ──► transcript.jsonl ────┐
├─► timeline.jsonl ─► report.md
clicks ──► capture hooks ──┐ │
terminal ──► asciinema ──────┴─► interactions.jsonl ┘
(the raw terminal.cast is kept alongside, archival)
page ──► rrweb ──► events.rrweb.jsonl (archival only; nothing downstream reads it)
Raw audio and video never leave your machine; only derived text is analysed. See privacy.
One line, no admin rights required (binary goes to ~/.local/bin; the download
is verified against the release's published checksums and, when an
authenticated GitHub CLI (gh) is available, its SLSA build-provenance
attestation):
curl -fsSL https://raw.githubusercontent.com/REPPL/Testimony/main/install.sh | shThe installer then offers to set up the pipeline's two dependencies — ffmpeg,
which record's capture (and transcribe -audio's conversion) needs, and a
local ASR engine (WhisperX or whisper.cpp) for transcribe — via Homebrew
where available, or as user-local installs for machines without admin rights. Prefer to read before you
run (sensible), or pass flags:
curl -fsSLO https://raw.githubusercontent.com/REPPL/Testimony/main/install.sh
less install.sh && sh install.sh # inspect first
curl -fsSL .../install.sh | sh -s -- --no-deps # binary only
curl -fsSL .../install.sh | sh -s -- --yes # non-interactive, with dependenciesOr build from source (requires Go): git clone this repository, then
go install ./cmd/testimony. Engine options and setup:
transcribe a recording.
Try the pipeline on the bundled synthetic session (needs a git clone of this
repository — the installed binary alone does not carry examples/):
testimony merge -session examples/sample-session
testimony report -session examples/sample-session
open examples/sample-session/report.mdThen capture a real one: testimony record -demo starts a capture session —
recording your voice and clicks in one command — and prints every step. The
session lands in ~/Testimony/sessions, the same place whatever directory you
run from; -out DIR puts it somewhere else. Voice
and screen capture need macOS; elsewhere, record skips those streams and
says so, and an external recording joins the session via transcribe -audio.
The getting-started tutorial walks the
whole path — record, think aloud, transcribe, merge, report — in about five
minutes. The result interleaves speech with interface events:
**[00:22] P1:** “Hm. I clicked save and nothing happened. No message, no
spinner. I can't actually tell if it saved.”
- [00:24] click `[data-testid=save-btn]` "Save" (#general)
The demo app contains at least one intentional usability flaw. Find it by talking.
- Tutorials — your first session, end to end.
- How-to guides — transcribe a recording (engines, languages, offsets), record a terminal session (asciinema, two windows, one import), analyse a session (findings and verdicts), draft regression tests (drafts and decisions), instrument your own app.
- Reference — the command line and the session directory.
- Explanation — how alignment works, privacy.
Each session is one folder of small, inspectable files, created under ~/Testimony/sessions unless -out names another root:
~/Testimony/sessions/<timestamp>/
manifest.json # app, participant, tasks, t0_epoch_ms (the shared clock anchor)
audio.wav # 16 kHz mono ASR input, captured or converted (local only)
audio.offset.json # audio→session offset for an external recording (local only)
screen.mp4 # screen capture, with record -video (local only)
events.rrweb.jsonl # raw rrweb stream (archival)
terminal.cast # raw asciicast, as recorded (archival; local only)
interactions.jsonl # normalised interaction events
transcript.jsonl # time-aligned utterances
timeline.jsonl # merged, session-relative timeline
findings.jsonl # analysis findings + verdicts
tests.jsonl # regression-test drafts + decisions
report.md # human-readable aligned record
Exact schemas: session directory reference.
Working today: record (managed capture — one command starts the recorders and
stamps the session), demo (instrumented capture), transcribe (local WhisperX
or whisper.cpp), import (an asciinema terminal recording joins the session's
interaction stream on the shared clock), merge, report, the first-pass
analysis layer — analyze (emit an analysis request, then validate the answer
into findings, recording the backend and model you declare answered it) and
review (record human verdicts) — and the regression-test
drafting layer, draft-tests (turn a confirmed finding into a proposed test
case, then render the accepted ones as a Markdown test plan) with
review -kind tests for the accept / edit / reject pass. record captures the
microphone by default; screen video is opt-in with -video. The model work is
host-delegated — the CLI never calls a model, holds no keys, and adds no network
dependency — every finding is unverified until you confirm or reject it, and
every drafted test is a proposal until you accept it. Run the analysis request
against a model on your own machine and no session content leaves it at any
step; findings.jsonl and report.md carry your declaration that it did
(analyse a session locally).
Coming next, in user terms:
- Codebase mapping — findings anchored to your code through the
data-testidselectors they were captured against. - Reference capture — narrated sessions over third-party apps, building a tagged corpus of design preferences.
- A macOS app wrapping the CLI core; Linux stays CLI-only.
MIT — see LICENSE.