#+TITLE: Handoff from work: the meeting transcription service needs an install home #+AUTHOR: Craig Jennings * What this is A self-hosted meeting transcription service (whisper.cpp plus pyannote speaker diarization) that runs on ratio, with velox as the offline fallback. It has been running on both machines since 2026-09-17. The code arrives as meeting-transcription-service.tar.gz alongside this note. I picked archsetup as its home because it is machine setup: a worker, two systemd user units, a Python venv and a model file. The client script and its Emacs backend entry are handled separately. * How it works - A job queue under ~/.local/state/meeting-transcribe/ with incoming/, work/, done/ and failed/. A systemd user path unit (meeting-transcribe.path) starts a oneshot worker (meeting-transcribe.service) when a job lands in incoming/. - The worker (src/transcribe-worker) converts audio to 16 kHz mono, runs whisper-cli at word level, runs pyannote (speaker-diarization-community-1) through src/diarize.py with the job's speaker count, and merges the two by timestamp with src/merge_transcript.py. One job at a time, behind a lock. - A finished job leaves done/.txt. A failed job leaves failed/.log. Nothing half-written reaches done/. - No network listener. Tailscale ssh is the transport and the login, systemd is the daemon, the filesystem is the queue. * What the install has to provide, per machine - ~/.local/share/pyannote-diarize/.venv :: Python 3.12, torch (CPU build), pyannote.audio 4.0.7. About 1.3 GB. Built with uv. - ~/.local/share/whisper-models/ggml-large-v3-turbo-q5_0.bin :: the whisper model; ratio's and velox's copies have the same checksum. whisper-cpp itself must be installed (it was already on velox). - The src/ scripts placed where the units expect them, and the two user units enabled. - Linger on, so the path unit runs without a login session. - One-time, online, by hand: a Hugging Face token and acceptance of the pyannote model terms, so the diarization model can be cached. After that neither machine needs Hugging Face. The token is a credential: it must not be written into this repo, which is publicly cloneable. * State today - Installed by hand on ratio and velox; both verified. No NVIDIA GPU and no ROCm on ratio, so it is CPU only. - make check in the bundle runs pytest (129 tests; whisper, pyannote, ssh and scp are faked at the process boundary), pyright and shellcheck. All green on 2026-09-19. - Known rough edge: when two local runs overlap, the second finds the lock held, the worker returns silently, and the client says "finished without producing a transcript". Rerunning fixes it, but the message should say the lock was held. * What I'm asking archsetup for Take ownership of the service side: the worker, diarize.py, merge_transcript.py, the two units, and an install step that builds the venv, fetches the model and enables the units on both daily drivers. Keep anything work-specific out of the repo; the code bundle has none (scanned before sending).