Any video, audio, or podcast → key takeaways. Transcribed locally, cached forever.
English | 繁體中文
An agent skill — open SKILL.md standard, works in
Claude Code and Codex —
that turns long-form media into 3–7 key
takeaways + a summary. Transcription runs locally with whisper and is cached by content hash —
while a cache entry exists, the same source is not transcribed again (unless you --force
). Ask for a different angle later and it re-digests from cache in seconds.
First-run transcription time depends on your hardware, model, and backend — after that, the cache answers.
Watching a 90-minute talk to extract 5 useful points is a bad trade. Sending audio to a cloud API costs money and leaks content. And summarizing the same episode twice — because the first summary had the wrong focus — means paying the transcription cost all over again.
Without audio-tldr With audio-tldr
────────────────── ───────────────
watch the whole video paste the URL
take notes by hand get takeaways + summary
"summarize it differently…" re-digest from cache, instant
re-upload, re-transcribe, re-pay transcribe once, reuse from cache
- ✓ YouTube, podcasts, and any yt-dlp-supported URL — or local audio/video files
- ✓ Local media pipeline: download, transcription, cache all run on your machine — audio is never uploaded (see Privacy) - ✓ Content-hash cache: re-summarizing (any angle) reuses the transcript while the entry exists
- ✓ Whisper backend auto-detection: mlx-whisper / faster-whisper / whisper.cpp / openai-whisper
- ✓ Language auto-detection; optional Simplified→Traditional Chinese conversion (OpenCC)
- ✓ Cache management built in: list, clear one, clear all, opt-in retention
- ✓ Timeline for long content (> 20 min)
- ✓ Digests saved to an output folder as Markdown or HTML — transcripts stay in the cache
- ✓ Conversational digest prompt: no request stated? The agent asks in plain text, listing the template menu
- ✓ Digest templates: meeting minutes, key summary, analysis report — or save your own reusable format
- ✓ Translation at the digest layer: digests in any language, or a faithful full-transcript translation
- ✓ Optional preferences file for standing habits — zero setup required
- ✓ Interpreter auto-selection: backend installed in another Python (e.g. Homebrew) is found and used automatically;
--doctor
diagnoses the environment - ✓ Apple Podcasts fallback built in: when yt-dlp's extractor fails, episodes resolve via the iTunes lookup API — cache identity stays on your original link; a show link (no episode id) automatically uses the latest episode
- ✓ Opt-in frame extraction for video sources: scene-detection slide capture, or stills at exact timestamps — video fetched at ≤720p and deleted after extraction; frames share the transcript's cache entry
- ✓ Install by copy, as a Claude Code plugin, or into Codex (open SKILL.md standard)
Option A — copy the skill (simplest):
git clone https://github.com/AugustusW/audio-tldr-skill.git
cp -r audio-tldr-skill/skills/audio-tldr ~/.claude/skills/
Invoke with /audio-tldr
, or just ask Claude to summarize a video — it auto-triggers.
Option B — install as a plugin:
/plugin marketplace add AugustusW/audio-tldr-skill
/plugin install audio-tldr@audio-tldr-skill
Invoke with /audio-tldr:audio-tldr
. Both options can coexist — plugin skills are namespaced.
Option C — Codex CLI / ChatGPT app:
The skill follows the open SKILL.md standard, so it works in Codex as-is. Copy the skill folder into Codex's skills directory:
git clone https://github.com/AugustusW/audio-tldr-skill.git
cp -r audio-tldr-skill/skills/audio-tldr ~/.codex/skills/audio-tldr # personal
Invoke it with a $audio-tldr
mention, or let Codex pick it implicitly when you ask to
summarize audio/video. The transcript cache (~/.cache/audio-tldr/
) and the preferences file
(~/.config/audio-tldr/preferences.md
) are shared with Claude Code — transcribe once, digest anywhere.
The media pipeline — download, transcription, cache — runs entirely on your machine.
| Requirement | Why | Install |
|---|---|---|
| Python 3.9+ | runs the transcription script | usually preinstalled |
yt-dlp |
||
| download audio from URLs | pip install yt-dlp or brew install yt-dlp |
|
ffmpeg |
||
| audio extraction/conversion | brew install ffmpeg / apt install ffmpeg |
|
| One whisper backend | ||
| speech-to-text | table below |
Whisper backends, in the order the skill auto-detects them:
| Backend | Best for | Install | Default model |
|---|---|---|---|
pip install mlx-whisper
large-v3-turbo
faster-whisperpip install faster-whisper
large-v3-turbo
whisper.cppbrew install whisper-cpp
- set
AUDIO_TLDR_WHISPER_CPP_MODEL
openai-whisperpip install openai-whisper
large-v3-turbo
Local files don't need yt-dlp
— only a whisper backend.
For URL sources, make sure you have the right to download and process the content, and comply with the source site's terms and your local copyright law.
The default is large-v3-turbo
on every backend (whisper.cpp excepted — its model is the
AUDIO_TLDR_WHISPER_CPP_MODEL
file). On CPU-only machines this favors quality over speed —
drop to small
if transcription is too slow. Override per run with --model
, or persistently
with AUDIO_TLDR_MODEL
(the flag wins). Bare names are mapped per backend (mlx gets the
mlx-community/whisper-
prefix automatically; a full HF repo path is used as-is):
| Situation | Suggested model |
|---|---|
| CPU / quick tests | small |
| General Chinese summaries | medium |
| Names, jargon, accuracy-critical | large-v3 |
| Capable GPU, speed + quality | large-v3 or large-v3-turbo |
python3 scripts/transcribe.py --model small "<source>" # per run
$env:AUDIO_TLDR_MODEL = "large-v3" # persistent; PowerShell (bash/zsh: export AUDIO_TLDR_MODEL=large-v3)
Optional — Traditional Chinese: whisper often emits Simplified Chinese. pip install opencc
and Chinese transcripts are converted to Taiwan Traditional automatically — including
common-phrase localization (s2twp
, e.g. 軟件→軟體) — plus the model is biased toward Traditional vocabulary. Not installed → transcripts are left as-is.
Windows is supported by the underlying Python stack, but the full flow has not yet been verified on Windows — reports welcome. Install with PowerShell:
winget install Gyan.FFmpeg
winget install yt-dlp.yt-dlp
py -3 -m pip install faster-whisper # recommended backend on Windows
git clone https://github.com/AugustusW/audio-tldr-skill.git
$skillsDir = "$env:USERPROFILE\.claude\skills"
New-Item -ItemType Directory -Force -Path $skillsDir | Out-Null
Copy-Item -Recurse -Force "audio-tldr-skill\skills\audio-tldr" $skillsDir
Manual copy does not auto-update, and -Force
overwrites an existing audio-tldr
folder — prefer the plugin install if you want managed versions.
Python command— ifpython3
isn't recognized, usepython
or the py launcher (py -3
); the skill tells Claude to fall back automatically, but substitute accordingly when running the script yourself.Skill path— Claude Code on Windows reads skills from%USERPROFILE%\.claude\skills\
(plugin install works identically to macOS/Linux).GPU (optional)— faster-whisper runs on CPU out of the box. NVIDIA acceleration goes through CTranslate2; check that a CUDA device is visible withpy -3 -c "import ctranslate2; print(ctranslate2.get_cuda_device_count())"
. Non-zero means CTranslate2 can see the GPU — it doesnot guarantee the CUDA runtime, cuBLAS/cuDNN DLLs, and GPU model all work; run one short real transcription to confirm. Required CUDA/cuDNN versions: see thefaster-whisper README.- mlx-whisper is Apple-Silicon-only. whisper.cpp on Windows needs a
whisper-cli.exe
on PATH plusAUDIO_TLDR_WHISPER_CPP_MODEL
.
> summarize https://www.youtube.com/watch?v=xxxx
> give me the key points from this podcast: https://podcasts.apple.com/...
> /audio-tldr ~/Downloads/meeting-recording.m4a
> summarize this talk for a beginner — action items only: https://youtu.be/xxxx
> (later) same video, but focus only on what they said about pricing
State your needs in the request — focus, audience, format, length, language — and the digest follows them instead of the default takeaways+summary structure. The last one re-uses the cached transcript — instant, no re-transcription.
Pairs well with— once the digest is written, "share this as a doc" turns it into a link you can hand to anyone (append, extend, or revoke it later).[sharedoc-mcp]
> summarize this talk and grab the slides: https://youtu.be/xxxx
> screenshots at 1:30 and 12:05 from ~/Videos/keynote.mp4
Asking for screenshots / slides runs scripts/frames.py
: ffmpeg scene detection captures
frames where the picture visibly changes (--threshold
, --min-gap
, --max-frames
), or
--at 90,12:05
extracts stills at exact timestamps (e.g. to illustrate a digest timeline).
Off by default — plain summarize requests never download video. For URLs the video is
fetched at ≤720p and deleted right after extraction (--keep-video
keeps it); local files
are used in place and never modified. Frames and their manifest.json
live in the same cache entry as the transcript, so repeated requests are instant. Pure logic is covered by automated tests; real-video extraction is verified manually per release.
Two phases, deliberately separated:
Transcribe(scripts/transcribe.py
) — resolves a cache key (normalized URL or file content hash), returns instantly on a hit; otherwise downloads via yt-dlp, transcribes with the best available whisper backend, and cachestranscript.txt
+meta.json
under~/.cache/audio-tldr/<sha256>/
.Digest— the agent reads the cached transcript and produces takeaways, a summary, and (for long content) an approximate timeline. If your request didn't say how to digest, it asks first — in plain conversational text, never a clickable menu, so it works over plain-text messaging channels too. Every digest is also saved to the output folder (default./audio-tldr-output/
) as<title>-<date>-<style>.md
(or.html
). Re-digesting with a different focus skips phase 1 entirely.
Be precise about what stays local and what doesn't:
Your audio/video never leaves the machine. No third-party transcription service is used, and the scripts in this repo contain no telemetry. Network access still happens where you'd expect: yt-dlp fetches URL sources from the source site, and whisper backends may download their model on first use (dependency behavior is governed by those projects). -
The digest phase sends the transcript text (never the audio) to the model, inside your own Claude session — exactly like asking Claude to read any local file. -
Cached transcripts are unencrypted plaintext, kept indefinitely by default, under~/.cache/audio-tldr/
. After processing sensitive content,--clear
that entry, or configure a retention period. -
Digests persist in the output folder(default./audio-tldr-output/
, relative to your working directory) — including full-transcript translations, which carry essentially the whole transcript. The output folder has no clearing or retention mechanism; delete files manually, and add the folder to.gitignore
if you run the skill inside a git-tracked directory. -
Phase 1 only (sensitive recordings): transcribe without ever handing the text to Claude — run the script yourself; stdout is metadata JSON only, and the transcript stays at the returnedtranscript_path
until you delete it:
python3 ~/.claude/skills/audio-tldr/scripts/transcribe.py "/path/to/recording.m4a"
py -3 "$env:USERPROFILE\.claude\skills\audio-tldr\scripts\transcribe.py" "C:\path\to\recording.m4a"
Create ~/.config/audio-tldr/preferences.md
to set standing habits — every field is optional and everything works without the file:
output_dir: ~/Documents/audio-digests
timeline: off
auto_delete_audio: off
output_format: html
model: large-v3
| field | default | meaning |
|---|---|---|
output_dir |
||
./audio-tldr-output |
||
| where digest files are saved | ||
timeline |
||
on |
||
| include a timeline section in digests when content warrants it | ||
auto_delete_audio |
||
on |
||
delete downloaded audio after transcription; off keeps the mp3 in the cache entry |
||
output_format |
||
md |
||
digest file format, md or html ; a per-request choice always wins |
||
model |
||
large-v3-turbo |
||
whisper model for transcription (passed as --model ); a per-request choice always wins |
||
digest_model |
||
| (platform default) | model for the digest subagent — unset = platform default (Claude Code: sonnet ; Codex: GPT-5.6 Terra ); a model name pins it; off = digest inline on the current agent (typically pricier) |
The file is read by the agent (Claude Code and Codex share it) — the install never asks you to set it up, and defaults apply whenever it's absent.
Three built-in templates shape the digest output — name one ("digest this as meeting minutes") or pick from the menu when asked:
| Template | What you get |
|---|---|
meeting-minutes |
|
| Meta, topics discussed, decisions, action items, open questions | |
key-summary |
|
| Key takeaways, one-paragraph summary, optional timeline (the default) | |
analysis-report |
|
| Arguments with evidence, data points, perspectives, implications |
The timeline in key-summary
appears only when the timeline
preference is not
off
, the source runs over 20 minutes, and the transcript has clear topic shifts.
Build your own: drop a markdown file in ~/.config/audio-tldr/templates/
—
frontmatter (name
, description
) plus section instructions; same name overrides a
built-in, a new name becomes a new menu option. Easiest start: copy a built-in from
skills/audio-tldr/templates/
and edit (e.g. change the timeline threshold). You can also just describe a format in conversation — the skill offers to save it for reuse. Your templates live outside the skill folder, so skill updates never touch them.
Cheaper digests: on platforms with subagents the digest runs on a cheaper model
by default (Claude Code: sonnet
; Codex: GPT-5.6 Terra
) — see the digest_model
preference to pin a model or turn this off (off
= digest inline).
The cache is kept forever by default — nothing is auto-deleted unless you opt in.
Ask Claude, or run scripts/transcribe.py
directly:
| Command | What it does |
|---|---|
--cache-info |
|
| list cached transcripts + sizes (JSON) | |
--clear "<source>" |
|
| delete one entry | |
--clear-all --yes |
|
| delete everything | |
--set-retention <days> |
|
auto-prune entries older than N days (off = keep forever) |
|
--force |
|
| re-transcribe one source, ignoring cache | |
--keep-audio |
|
| keep the downloaded mp3 in the cache entry (default deletes it after transcription) | |
--doctor |
|
| JSON environment diagnosis: Python path/version, backend & tool visibility, other interpreters that have a backend, MLX Metal availability |
Environment variables:
| Variable | Purpose |
|---|---|
AUDIO_TLDR_MODEL |
|
override the whisper model for the active backend (--model beats it) |
|
AUDIO_TLDR_WHISPER_CPP_MODEL |
|
| path to a ggml model file (enables the whisper.cpp backend) | |
AUDIO_TLDR_ZH_CONVERT |
|
Chinese conversion: off , or an OpenCC config (default s2twp — Taiwan Traditional incl. common phrases) |
|
AUDIO_TLDR_PYTHON |
|
| pin the Python interpreter the script runs under (wins over auto-probing). Useful when your whisper backend lives in a non-default Python (e.g. Homebrew 3.12) |
git clone https://github.com/AugustusW/audio-tldr-skill.git
cd audio-tldr-skill
python3 -m pytest tests/ # 93 unit tests, no network or model needed
Versioning: every release bumps version
in .claude-plugin/plugin.json
and
.claude-plugin/marketplace.json
(kept identical), adds a CHANGELOG entry,
and is published as a git tag + GitHub Release.
To get update notifications: Watch this repo (Custom → Releases), or — if you installed as a
Claude Code plugin — run /plugin
and update from the marketplace (it compares the version above).
Manual-copy installs have no auto-update: re-copy the skill folder after a new release.
Your preferences, custom templates (~/.config/audio-tldr/
), and cache
(~/.cache/audio-tldr/
) all live outside the skill folder — updating never touches them.
v0.4.0 (CHANGELOG) — core logic is covered by 63 offline unit tests (yt-dlp,
whisper backends, cache, and OpenCC are mocked; no network or models needed). The full flow has
been manually verified (2026-07-19: real YouTube download, transcription, cached re-digest,
Chinese conversion, --keep-audio
, output-folder digests in md/html, transcript translation,
interpreter auto-selection from /usr/bin/python3
, and the Apple Podcasts fallback end-to-end — a real 53-min episode resolved via iTunes lookup, transcribed, and cache-hit on the original Apple URL) on:
| Component | Verified version |
|---|---|
| macOS | 26.5.1 (Apple M4 Pro) |
| Python | 3.12.13 |
| mlx-whisper | 0.4.3 |
| ffmpeg | 8.1 |
| yt-dlp | 2026.06.09 |
Newer dependency versions may behave differently. Not yet covered by automated tests: real downloads, the other three backends, and Windows. Codex support follows the open SKILL.md standard; the transcription core was verified end-to-end inside Codex on 2026-07-19 (a real 53-min podcast downloaded, transcribed, and cache-hit, including the interpreter auto-selection path). Digest-layer features (output folder, translation, preferences) have so far been exercised in Claude Code only. Possible next: SRT export, speaker diarization. Issues and PRs welcome.
MIT. See LICENSE.
Long content is worth hearing once — by your machine, not by you.