Downloads YouTube video transcripts/subtitles and cover images by URL or video ID. Supports multiple languages, translation, chapters, and speaker identification. Caches raw data for fast re-formatting. Use when user asks to "get YouTube transcript", "download subtitles", "get captions", "YouTube字幕", "YouTube封面", "视频封面", "video thumbnail", "video cover image", or provides a YouTube URL and wants the transcript/subtitle text or cover image extracted.
YouTube Transcript
下載 YouTube 影片的字幕(包含手動建立與自動產生)。無需 API 金鑰或瀏覽器,直接使用 YouTube 的 InnerTube API,並在 YouTube 阻擋直接 API 路徑時自動降級使用 yt-dlp。
首次執行時會擷取影片中繼資料與封面圖片,並快取原始資料以便快速重新格式化。
腳本目錄
腳本位於 scripts/ 子目錄。{baseDir} 代表此 SKILL.md 所在的目錄路徑。解析 ${BUN_X} 執行環境:若已安裝 bun → 使用 bun;若可使用 npx → 使用 npx -y bun;否則建議安裝 bun。請將 {baseDir} 與 ${BUN_X} 替換為實際值。
| 腳本 | 用途 |
|---|---|
scripts/main.ts |
字幕下載命令列工具 |
使用方式
# 預設:含時間戳記的 Markdown(英文)
${BUN_X} {baseDir}/scripts/main.ts <youtube-url-or-id>
# 指定語言(優先順序)
${BUN_X} {baseDir}/scripts/main.ts <url> --languages zh,en,ja
# 不含時間戳記
${BUN_X} {baseDir}/scripts/main.ts <url> --no-timestamps
# 含章節分段
${BUN_X} {baseDir}/scripts/main.ts <url> --chapters
# 含說話者辨識(需 AI 後處理)
${BUN_X} {baseDir}/scripts/main.ts <url> --speakers
# SRT 字幕檔
${BUN_X} {baseDir}/scripts/main.ts <url> --format srt
# 翻譯字幕
${BUN_X} {baseDir}/scripts/main.ts <url> --translate zh-Hans
# 列出可用字幕
${BUN_X} {baseDir}/scripts/main.ts <url> --list
# 強制重新擷取(忽略快取)
${BUN_X} {baseDir}/scripts/main.ts <url> --refresh
選項
| 選項 | 說明 | 預設值 |
|---|---|---|
<url-or-id> |
YouTube 網址或影片 ID(可多個) | 必填 |
--languages <codes> |
語言代碼,逗號分隔,依優先順序 | en |
--format <fmt> |
輸出格式:text、srt |
text |
--translate <code> |
翻譯至指定語言代碼 | |
--list |
列出可用字幕,不擷取 | |
--timestamps |
每段加上 [HH:MM:SS → HH:MM:SS] 時間戳記 |
開啟 |
--no-timestamps |
停用時間戳記 | |
--chapters |
從影片說明解析章節分段 | |
--speakers |
輸出含中繼資料的原始字幕供說話者辨識 | |
--exclude-generated |
跳過自動產生的字幕 | |
--exclude-manually-created |
跳過手動建立的字幕 | |
--refresh |
強制重新擷取,忽略快取 | |
-o, --output <path> |
儲存至指定檔案路徑 | 自動產生 |
--output-dir <dir> |
輸出基礎目錄 | youtube-transcript |
選用環境變數
| 變數 | 說明 |
|---|---|
YOUTUBE_TRANSCRIPT_COOKIES_FROM_BROWSER |
降級時傳遞給 yt-dlp --cookies-from-browser,例如 chrome、safari、firefox 或 chrome:Profile 1 |
輸入格式
接受以下任一格式作為影片輸入:
- 完整網址:
https://www.youtube.com/watch?v=dQw4w9WgXcQ - 短網址:
https://youtu.be/dQw4w9WgXcQ - 嵌入網址:
https://www.youtube.com/embed/dQw4w9WgXcQ - Shorts 網址:
https://www.youtube.com/shorts/dQw4w9WgXcQ - 影片 ID:
dQw4w9WgXcQ
輸出格式
| 格式 | 副檔名 | 說明 |
|---|---|---|
text |
.md |
Markdown,含 frontmatter(包含 description)、標題、摘要、可選目錄/封面/時間戳記/章節/說話者 |
srt |
.srt |
SubRip 字幕格式,適用於影片播放器 |
輸出目錄
youtube-transcript/
├── .index.json # 影片 ID → 目錄路徑對應(供快取查詢)
└── {channel-slug}/{title-full-slug}/
├── meta.json # 影片中繼資料(標題、頻道、說明、長度、章節等)
├── transcript-raw.json # 從 YouTube API 取得的原始字幕片段(已快取)
├── transcript-sentences.json # 依句子分割的字幕(依標點符號分割,合併跨片段內容)
├── imgs/
│ └── cover.jpg # 影片縮圖
├── transcript.md # Markdown 字幕(從句子產生)
└── transcript.srt # SRT 字幕(從原始片段產生,若使用 --format srt)
{channel-slug}:頻道名稱,以 kebab-case 表示{title-full-slug}:完整影片標題,以 kebab-case 表示
--list 模式僅輸出至標準輸出(不儲存檔案)。
快取
首次擷取時,腳本會儲存:
meta.json— 影片中繼資料、章節、封面圖片路徑、語言資訊transcript-raw.json— 從 YouTube API 取得的原始字幕片段({ text, start, duration }[])transcript-sentences.json— 依句子分割的字幕({ text, start: "HH:mm:ss", end: "HH:mm:ss" }[]),依句尾標點(.?!…。?!等)分割,時間戳記依字元長度比例分配,支援 CJK 文字合併imgs/cover.jpg— 影片縮圖
後續對同一影片的執行會使用快取資料(無網路請求)。使用 --refresh 強制重新擷取。若請求不同語言,快取會自動更新。
當 YouTube 對直接 InnerTube 路徑回傳反機器人/封鎖回應時,腳本會先嘗試其他客戶端身份,然後降級使用 yt-dlp(若可用)。若需降級但 yt-dlp 不可用,代理應自行設法讓 yt-dlp 可用並繼續,而非將安裝決定推給使用者。
SRT 輸出(--format srt)從 transcript-raw.json 產生。文字/Markdown 輸出使用 transcript-sentences.json 以獲得自然的句子邊界。
工作流程
當使用者提供 YouTube 網址並要求字幕時:
- 若使用者未指定語言,先使用
--list列出可用選項 - 執行腳本時務必將網址用單引號括起來 — zsh 會將
?視為 glob 萬用字元,未加引號的 YouTube 網址會導致「no matches found」錯誤:請使用'https://www.youtube.com/watch?v=ID' - 預設:使用
--chapters --speakers以獲得最豐富的輸出(章節 + 說話者辨識) - 腳本會自動儲存快取資料與輸出檔案,並列印檔案路徑
- 對於
--speakers模式:腳本儲存原始檔案後,請依照下方的說話者辨識工作流程進行後處理,加上說話者標籤
當使用者僅需要封面圖片或中繼資料時,使用任何選項執行腳本也會快取 meta.json 與 imgs/cover.jpg。
當需要重新格式化同一影片(例如先輸出文字再輸出 SRT)時,會重複使用快取資料,無需重新擷取。
章節與說話者工作流程
章節(--chapters)
腳本會從影片說明中解析章節時間戳記(例如 0:00 Introduction),依章節邊界分割字幕,將片段分組為可讀段落,並儲存為含目錄的 .md 檔案。無需進一步處理。
若說明中無章節時間戳記,則字幕會以分組段落輸出,不含章節標題。
說話者辨識(--speakers)
說話者辨識需要 AI 處理。腳本會輸出原始 .md 檔案,包含:
- YAML frontmatter,含影片中繼資料(標題、頻道、日期、封面、說明、語言)
- 影片說明(用於提取說話者名稱)
- 來自說明的章節列表(若有的話)
- 原始字幕,以 SRT 格式呈現(預先計算開始/結束時間戳記,節省 token)
腳本儲存原始檔案後,請啟動子代理(為節省成本,建議使用較便宜的模型如 Sonnet)來處理說話者辨識:
- 讀取已儲存的
.md檔案 - 讀取
{baseDir}/prompts/speaker-transcript.md的提示模板 - 依照提示處理原始字幕:
- 使用影片中繼資料辨識說話者(標題 → 來賓、頻道 → 主持人、說明 → 名稱)
- 從對話流程、問答模式與上下文線索偵測說話者輪替
- 分割為章節(若說明中有章節則使用,否則依主題轉換建立)
- 使用
**Speaker Name:**標籤、段落分組(2-4 句)與[HH:MM:SS → HH:MM:SS]時間戳記格式化
- 將處理後的字幕覆寫回
.md檔案(保留 YAML frontmatter)
使用 --speakers 時,--chapters 會隱含啟用 — 處理後的輸出一定包含章節分段。
錯誤情況
| 錯誤 | 意義 |
|---|---|
| Transcripts disabled | 影片完全沒有字幕 |
| No transcript found | 請求的語言不可用 |
| Video unavailable | 影片已刪除、設為私人或受地區限制 |
| IP blocked | 請求過多,請稍後再試 |
| Age restricted | 影片需要登入進行年齡驗證 |
| bot detected | 腳本會重試其他客戶端,然後使用 yt-dlp;若缺少降級工具,代理應自行解決;若仍失敗,可嘗試 YOUTUBE_TRANSCRIPT_COOKIES_FROM_BROWSER=safari(或你的瀏覽器) |






