YouTube Transcripts v0.15

Extract full transcripts from any YouTube video — no API key, no OAuth, no scraping. WebPeel fetches the caption track directly from YouTube's public timedtext endpoint.

What It Does

Pass any YouTube URL to WebPeel and get back the full transcript as time-stamped segments. Works with auto-generated captions and manually uploaded subtitle tracks. No YouTube Data API v3 key required — this is completely free and unlimited.

Supported URL Formats

All standard YouTube URL patterns are recognised automatically:

Format Example
Standard watch https://www.youtube.com/watch?v=dQw4w9WgXcQ
Short URL https://youtu.be/dQw4w9WgXcQ
Embed https://www.youtube.com/embed/dQw4w9WgXcQ
Shorts https://www.youtube.com/shorts/dQw4w9WgXcQ
Mobile https://m.youtube.com/watch?v=dQw4w9WgXcQ

CLI

Just pass a YouTube URL — WebPeel auto-detects it and returns the transcript:

# Fetch transcript as plain text (default)
npx webpeel "https://youtube.com/watch?v=dQw4w9WgXcQ"

# JSON output with full segment metadata
npx webpeel "https://youtube.com/watch?v=dQw4w9WgXcQ" --json

# Specify language (default: en)
npx webpeel "https://youtu.be/dQw4w9WgXcQ" --language es --json

# Short-form Shorts URL
npx webpeel "https://youtube.com/shorts/dQw4w9WgXcQ" --json

API

Dedicated transcript endpoint — returns the full transcript with segment timestamps.

# Basic transcript
GET /v1/youtube?url=https://youtube.com/watch?v=dQw4w9WgXcQ

# Specify language
GET /v1/youtube?url=https://youtu.be/dQw4w9WgXcQ&language=en

# With API key
curl "https://api.webpeel.dev/v1/youtube?url=https://youtube.com/watch?v=dQw4w9WgXcQ" \
  -H "Authorization: Bearer YOUR_API_KEY"

Query Parameters

Parameter Type Description
url string (required) YouTube video URL (any supported format)
language string BCP-47 language code (default: en). Falls back to first available track.

MCP

Use the webpeel_youtube tool directly inside Claude, Cursor, or any MCP-compatible client:

{
  "tool": "webpeel_youtube",
  "arguments": {
    "url": "https://youtube.com/watch?v=dQw4w9WgXcQ",
    "language": "en"
  }
}

Or just use webpeel_fetch — YouTube URLs are auto-detected and the transcript is returned as the content field automatically.

Example Output

{
  "url": "https://youtube.com/watch?v=dQw4w9WgXcQ",
  "title": "Rick Astley - Never Gonna Give You Up (Official Music Video)",
  "channel": "Rick Astley",
  "duration": 213,
  "language": "en",
  "transcript": [
    { "start": 0.0,   "dur": 3.2,  "text": "We're no strangers to love" },
    { "start": 3.2,   "dur": 2.8,  "text": "You know the rules and so do I" },
    { "start": 6.0,   "dur": 3.5,  "text": "A full commitment's what I'm thinking of" },
    { "start": 9.5,   "dur": 4.0,  "text": "You wouldn't get this from any other guy" }
  ],
  "content": "We're no strangers to love\nYou know the rules and so do I\nA full commitment's what I'm thinking of\nYou wouldn't get this from any other guy\n..."
}

Response Fields

Field Type Description
url string Canonical YouTube URL
title string Video title
channel string Channel name
duration number Video duration in seconds
language string Language code of returned transcript
transcript array Time-stamped segments: { start, dur, text }
content string Full transcript as plain text (newline-separated)

SDK Usage

import { peel } from 'webpeel';

// YouTube URLs are auto-detected — just call peel()
const result = await peel('https://youtube.com/watch?v=dQw4w9WgXcQ');

// result.content contains the full transcript text
console.log(result.content);

// result.transcript has the time-stamped segments
result.transcript.forEach(seg => {
  console.log(`[${seg.start}s] ${seg.text}`);
});

// Specify a language
const spanish = await peel('https://youtu.be/dQw4w9WgXcQ', { language: 'es' });
from webpeel import WebPeel

client = WebPeel()

# YouTube URLs are auto-detected
result = client.scrape("https://youtube.com/watch?v=dQw4w9WgXcQ")
print(result.content)  # full transcript text

# With language
result = client.scrape(
    "https://youtu.be/dQw4w9WgXcQ",
    language="es"
)
for seg in result.transcript:
    print(f"[{seg['start']}s] {seg['text']}")
💡 Auto-Detection in peel()
You don't need to call a special method. Any YouTube URL passed to peel() is automatically routed to the transcript extractor. The content field will contain the full transcript text, ready to feed into an LLM.

Error Handling

If a video has no transcript (disabled or unavailable), WebPeel returns an error with a descriptive message:

{
  "error": "NO_TRANSCRIPT",
  "message": "No transcript available for this video. The uploader may have disabled captions.",
  "url": "https://youtube.com/watch?v=..."
}

Use the language parameter to fall back to a specific track, or omit it to get the first available track in any language.