Transcript Bunny documentation

YouTube Transcript API

Endpoints, authentication, examples, and rate limits for fetching YouTube transcripts as JSON.

API Keys

Transcript Bunny uses API keys to authenticate requests. All API requests must include your API key in the Authorization header.

Available on All Plans

API keys are available on every plan, including Free. Free plan usage is limited to 5 requests/minute and your monthly credit balance. Upgrade for higher limits.

Creating an API Key

  • 1. Navigate to API Keys page
  • 2. Enter a name for your API key
  • 3. Click "Create API Key"
  • 4. Copy your key immediately (it won't be shown again)

API Key Format: Your API keys will look like this:

tb_live_...

API Key Management

You can revoke your API keys at any time from the API Keys page. API keys use your account credits.

Using Your API Key

Include your API key in the Authorization header of every request:

Authorization: Bearer YOUR_API_KEY

Security Best Practices

  • • Never share your API keys publicly
  • • Store keys securely as environment variables
  • • Rotate keys regularly
  • • Delete unused keys immediately

Get Transcript Endpoint

Retrieve transcripts for public YouTube videos that have captions, programmatically.

Endpoint

POST https://transcriptbunny.com/api/v1/transcribe

Request Body

{
"videoUrl": "https://www.youtube.com/watch?v=dQw4w9WgXcQ"
}

Parameters

Parameter Type Required Description
videoUrl string Yes YouTube video URL
timestamps boolean No Set true to also receive transcript.timestampedText — the transcript as lines prefixed with [mm:ss] timestamps, ready to paste into an LLM prompt

Code Examples

const response = await fetch('https://transcriptbunny.com/api/v1/transcribe', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': 'Bearer YOUR_API_KEY'
},
body: JSON.stringify({
videoUrl: 'https://www.youtube.com/watch?v=dQw4w9WgXcQ'
})
});
const data = await response.json();
console.log(data);
import requests
response = requests.post(
'https://transcriptbunny.com/api/v1/transcribe',
headers={
'Content-Type': 'application/json',
'Authorization': 'Bearer YOUR_API_KEY'
},
json={
'videoUrl': 'https://www.youtube.com/watch?v=dQw4w9WgXcQ'
}
)
data = response.json()
print(data)
<?php
$ch = curl_init('https://transcriptbunny.com/api/v1/transcribe');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => [
'Content-Type: application/json',
'Authorization: Bearer YOUR_API_KEY'
],
CURLOPT_POSTFIELDS => json_encode([
'videoUrl' => 'https://www.youtube.com/watch?v=dQw4w9WgXcQ'
])
]);
$response = curl_exec($ch);
$data = json_decode($response, true);
print_r($data);
?>
require 'net/http'
require 'json'
uri = URI('https://transcriptbunny.com/api/v1/transcribe')
http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = true
request = Net::HTTP::Post.new(uri.path)
request['Content-Type'] = 'application/json'
request['Authorization'] = 'Bearer YOUR_API_KEY'
request.body = { videoUrl: 'https://www.youtube.com/watch?v=dQw4w9WgXcQ' }.to_json
response = http.request(request)
data = JSON.parse(response.body)
puts data
curl -X POST https://transcriptbunny.com/api/v1/transcribe \
-H "Content-Type: application/json" \
-H "Authorization: Bearer YOUR_API_KEY" \
-d '{"videoUrl": "https://www.youtube.com/watch?v=dQw4w9WgXcQ"}'

Other Endpoints

Get a stored transcript

GET https://transcriptbunny.com/api/v1/transcripts/:videoId

Returns a transcript this account already owns. Optional query timestamps=true adds transcript.timestampedText. Does not charge credits. 404 if this account has not transcribed the video.

Usage

GET https://transcriptbunny.com/api/v1/usage

Returns plan, credits.total/used/remaining, request counts, and billingPeriod. Same Bearer authentication as transcribe.

Response Format

Understanding the API response structure.

Success Response

When a transcript is successfully retrieved, you'll receive 200 OK for an account replay (0 credits) or a global cache hit (1 credit if this account has not acquired it yet), or 201 Created for a fresh upstream fetch:

{
"transcript": {
"text": "Hello, welcome to this video. This is a sample transcript.",
"segments": [
{
"text": "Hello, welcome to this video.",
"start": 0.0,
"end": 3.5,
"timestamp": "00:00"
},
{
"text": "This is a sample transcript.",
"start": 3.5,
"end": 6.2,
"timestamp": "00:03"
}
]
},
"video": {
"id": "dQw4w9WgXcQ",
"url": "https://www.youtube.com/watch?v=dQw4w9WgXcQ",
"title": "Example video",
"channelName": "Example Channel"
},
"source": "fetched",
"creditsCharged": 1,
"creditsRemaining": 999
}

Response Fields

Field Type Description
transcript object Transcript data with segments
transcript.text string Complete transcript as plain text
transcript.segments array Array of transcript segments with timestamps
transcript.timestampedText string Only when timestamps=true: transcript as [mm:ss]-prefixed lines (also on GET /api/v1/transcripts/:videoId?timestamps=true)
video object Video id, url, title, and channel name when available
source string fetched (new upstream fetch), global_cache (already stored for another account), or account_replay (this account already owns it)
creditsCharged number 0 for an account replay. 1 for a fresh fetch or a global cache hit for an account that has not requested this video before.
creditsRemaining number Your remaining credits after this request (only included when credits are charged)

Segment Object Structure

Field Type Description
text string Transcript text for this segment
start number Start time in seconds
end number End time in seconds
timestamp string Formatted timestamp (MM:SS)

Special Cases

Account replay

If this account already owns the transcript, you receive 200 OK with no credit charge:

{
"transcript": { ... },
"video": { ... },
"source": "account_replay",
"creditsCharged": 0,
"message": "You previously requested this video (no charge)"
}

A global cache hit is different: the transcript already exists on Transcript Bunny, but this account has never requested it. That still costs 1 credit and returns source: "global_cache".

Error Handling

Learn about error codes and how to handle them.

Error Response Format

When an error occurs, the API returns an appropriate HTTP status code and error details:

{
"error": "Insufficient credits",
"remaining": 0,
"upgrade": "https://transcriptbunny.com/pricing"
}

Common Error Codes

401 Unauthorized

Invalid or missing API key.

{
"error": "Missing or invalid Authorization header",
"docs": "https://transcriptbunny.com/docs"
}

Or: { "error": "Invalid API key" }

400 Bad Request

Invalid YouTube URL or missing parameters.

{
"error": "Invalid YouTube URL",
"message": "Please provide a valid YouTube video URL"
}

Or validation error: { "success": false, "error": { "issues": [...] } }

402 Payment Required

Insufficient credits to process the request.

{
"error": "Insufficient credits",
"remaining": 0,
"upgrade": "https://transcriptbunny.com/pricing"
}

404 Not Found

Video not found or transcript not available.

{ "error": "Transcript not found" }

Or: { "error": "Transcript not available", "message": "...", "creditsCharged": 0 }

429 Too Many Requests

Rate limit exceeded.

{
"error": "Rate limit exceeded",
"limit": 50,
"window": "60 seconds",
"retryAfter": 60,
"upgrade": "https://transcriptbunny.com/billing"
}

500 Internal Server Error

Server error processing your request.

{ "error": "Internal server error" }

Best Practices

  • Always check the HTTP status code first
  • Implement exponential backoff for rate limit errors
  • Log error responses for debugging
  • Check credits before making requests
  • Handle network errors gracefully

Rate Limits

Understanding API rate limits and best practices.

Rate Limit Rules

To ensure fair usage and system stability, we implement per-minute rate limits that vary by plan:

Free

5
requests per minute

Starter

50
requests per minute

Pro

100
requests per minute

Business

200
requests per minute

Credit Limits

Rate limits are separate from your credit allocation. Even with available credits, you must respect rate limits.

Response Headers

Successful API responses include rate limit information in the headers:

X-RateLimit-Limit: 50
X-RateLimit-Remaining: 48
X-RateLimit-Reset: 1609459200000

Note: Values shown are for Starter plan. Limits vary by plan. Headers are included on successful responses (200 OK). Rate limit errors (429) return error details in the JSON response body instead.

Header Descriptions

Header Description
X-RateLimit-Limit Maximum requests allowed in current window
X-RateLimit-Remaining Requests remaining in current window
X-RateLimit-Reset Unix timestamp in milliseconds when the rate limit resets

Handling Rate Limits

Example code for handling rate limits with exponential backoff:

async function fetchWithRetry(url, options, maxRetries = 3) {
for (let i = 0; i < maxRetries; i++) {
const response = await fetch(url, options);
if (response.status === 429) {
// Rate limit info is in response body
const error = await response.json();
const retryAfter = error.retryAfter || 60; // seconds until window resets
console.log(`Rate limited. Waiting ${retryAfter} seconds...`);
await new Promise(resolve => setTimeout(resolve, retryAfter * 1000));
continue;
}
return response;
}
throw new Error('Max retries exceeded');
}

Note: Rate limit errors return a 429 status with error details in the JSON response body, including retryAfter (seconds until the rate limit window resets).

Automation & Integration Tools

Use Transcript Bunny with popular automation platforms.

No-Code Integrations

Call the Transcript Bunny REST API from HTTP modules in Zapier, Make, n8n, or Pipedream. There is no native Zapier/Make app; you send POST /api/v1/transcribe with a Bearer token.

Zapier

Integrate with 5000+ apps using Zapier's Webhooks module.

Quick Setup:

  1. 1. Create a new Zap in Zapier
  2. 2. Choose "Webhooks by Zapier" as action
  3. 3. Select "POST" method
  4. 4. URL: https://transcriptbunny.com/api/v1/transcribe
  5. 5. Add header: Authorization: Bearer YOUR_API_KEY
  6. 6. Body: {"videoUrl": "YOUR_VIDEO_URL"}

Make (Integromat)

Build advanced automations with Make's visual builder.

Quick Setup:

  1. 1. Create a new scenario in Make
  2. 2. Add "HTTP" module
  3. 3. Choose "Make a request"
  4. 4. Method: POST
  5. 5. URL: https://transcriptbunny.com/api/v1/transcribe
  6. 6. Headers: Authorization with Bearer token
  7. 7. Body: JSON with video URL

n8n

Self-hosted workflow automation with full API control.

Quick Setup:

  1. 1. Create new workflow in n8n
  2. 2. Add "HTTP Request" node
  3. 3. Method: POST
  4. 4. URL: https://transcriptbunny.com/api/v1/transcribe
  5. 5. Authentication: Header Auth
  6. 6. Header Name: Authorization
  7. 7. Header Value: Bearer YOUR_API_KEY

Pipedream

Low-code integration platform with built-in triggers.

Quick Setup:

  1. 1. Create new workflow in Pipedream
  2. 2. Add HTTP request step
  3. 3. Configure POST request
  4. 4. Add Authorization header
  5. 5. Use Node.js code for advanced parsing

Example Workflows

Content Creation Workflow

Trigger: New video uploaded to YouTube → Get transcript → Generate summary with ChatGPT → Create blog post draft → Save to Notion

Educational Workflow

Trigger: New video in playlist → Get transcript → Extract key concepts → Create flashcards → Add to Anki deck

Research Workflow

Trigger: Manual trigger with URL → Get transcript → Analyze with AI → Extract citations → Save to Zotero