YouTube transcript API
Get a YouTube transcript from Python, Node or curl
POST the URL of a public YouTube video and get its transcript back as JSON: one segment per line with its start and end in seconds, and the full text. It needs an Apify API token, not a YouTube API key.
$0.01 per transcript. Failed videos are not charged.
Input and output
{
"urls": ["https://youtu.be/4czjS9h4Fpg"],
"lang": "en"
}Up to 100 video, channel or playlist URLs per run, 100 videos in total. lang defaults to en and falls back to the video’s original language.
{
"videoId": "4czjS9h4Fpg",
"title": "Perseverance Rover’s Descent and Touchdown on Mars (Official NASA Video)",
"lang": "en",
"segments": [
{ "start": 0.4, "end": 3.28, "text": "We are starting the straighten up and fly right maneuver," },
{ "start": 3.28, "end": 7.36, "text": "where the spacecraft will jettison the entry balance masses in preparation for" },
{ "start": 7.36, "end": 14.16, "text": "parachute deploy and to roll over to give the radar a better look at the ground." },
...
],
"text": "We are starting the straighten up and fly right maneuver, where the spacecraft will jettison the...",
"frameskimUrl": "https://apify.com/emttn/frameskim"
}The real transcript of NASA’s Perseverance descent video (courtesy NASA/JPL-Caltech): 30 segments, the first three shown, and the text shortened.
The same call in three languages
curl -X POST "https://api.apify.com/v2/acts/emttn~youtube-transcript/run-sync-get-dataset-items" \
-H "Authorization: Bearer $APIFY_TOKEN" \
-H "Content-Type: application/json" \
-d '{"urls": ["https://youtu.be/4czjS9h4Fpg"]}'import os, requests
res = requests.post(
"https://api.apify.com/v2/acts/emttn~youtube-transcript/run-sync-get-dataset-items",
headers={"Authorization": f"Bearer {os.environ['APIFY_TOKEN']}"},
json={"urls": ["https://youtu.be/4czjS9h4Fpg"]},
timeout=300,
)
item = res.json()[0]
print(item["segments"][0])const res = await fetch("https://api.apify.com/v2/acts/emttn~youtube-transcript/run-sync-get-dataset-items", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.APIFY_TOKEN}`,
"Content-Type": "application/json",
},
body: JSON.stringify({ urls: ["https://youtu.be/4czjS9h4Fpg"] }),
});
const [item] = await res.json();
console.log(item.segments[0]);From a cloud server or a CI runner
The request runs on Apify, which reaches YouTube through its datacenter and residential proxies, not through your server’s IP address. A video YouTube still blocks comes back as an item with error and is not charged.
Limits
- Videos need captions: it does not transcribe audio.
- Public videos, channels and playlists, up to 100 videos per run; each channel or playlist adds up to
maxVideosof its videos (20 by default). Searches are refused before anything runs, with nothing charged. - $0.01 per transcript delivered, pay per event on Apify, never above the spending limit you set.