Audio & Video Transcription
Pricing
from $4.50 / 1,000 audio minute transcribeds
Audio & Video Transcription
Transcribe audio and video links to text with timestamps, SRT and VTT: YouTube videos and channels, mp3 and mp4 files, Google Drive, Dropbox, podcast RSS feeds, Apple Podcasts, TikTok, Instagram. Long episodes. Optional speaker labels, translation, AI summary.
Pricing
from $4.50 / 1,000 audio minute transcribeds
Rating
0.0
(0)
Developer
Volodymyr Cherniaga
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
2
Monthly active users
29 minutes ago
Last modified
Categories
Share
Turn audio and video links into text. Paste a YouTube video, channel or playlist, a podcast feed, an Apple Podcasts link, a direct mp3 or mp4, or a TikTok, Instagram or Facebook video, and get the full transcript with timestamps and ready SRT and VTT subtitles. Hours-long episodes work. Turn on Speaker labels to see who said what, Translate to to get the transcript and subtitles in up to 5 other languages, and Summary, chapters and key points to also get a short summary and timestamped chapters.
$0.005 per audio minute, $0.0045 on Apify's Business plan and higher. Recordings without speech and links that fail are not charged.
Why use it
- One field for every kind of link. YouTube videos, channels and playlists, files, podcast RSS feeds, Apple Podcasts shows and episodes, video pages. The actor works out what is behind each link.
- YouTube without cookies or proxies. Videos, Shorts, a channel's newest videos or a playlist, at the same price per minute, with no per-video fee.
- Long recordings. A 3.6-hour podcast episode was transcribed in 9 minutes at the default memory. Recordings are split at pauses, so words are not cut in half, and the timestamps run continuously through the whole recording.
- About 100 languages, detected automatically. Tested on English, Spanish, German and Russian.
- Speaker labels. Every line can be marked Speaker 1, Speaker 2 and so on, also in the subtitles, with the whole dialogue in one field. A 3.3-hour interview is labelled in one pass, so the numbers stay the same from start to end.
- Whole shows in one run. A feed or a show link gives its newest episodes; set how many, and keep only episodes whose title contains (or does not contain) the words you give.
- Word timestamps, free. Every word with its start and end time, for karaoke captions, cutting clips or word-accurate search (for recordings the actor transcribes).
- Find mentions, free. List brands, names or topics in Find mentions of, and every mention comes back with its time, the phrase, the speaker and a link to that moment in the recording.
- Free when the podcast or video already has a transcript. Many podcast feeds list a transcript for each episode (Podcasting 2.0), and many YouTube videos have captions uploaded by their author (TED, for example). The actor uses them instead of transcribing, and the audio minutes are not charged.
- Translation into up to 5 languages in one run, each with its own text and SRT and VTT subtitles on the same timestamps.
- Only new episodes on a schedule. Turn on Only new episodes and every later run transcribes and charges only what it has not seen before.
- No charge for silence or instrumental music. A recording with no speech comes back with
speech: falseand is not billed. Songs with vocals count as speech: the lyrics are transcribed. - No API keys, no login, no proxies to set up.
What you get
One row per recording.
| Field | What it is |
|---|---|
text | the full transcript |
segments | the transcript in lines, each with start and end in seconds, and speaker with the speaker option; with Word timestamps, words: every word with its start and end |
wordsIncomplete | only with Word timestamps, when some lines have no words: the podcast's own transcript and YouTube author captions have no word times, and rarely a part of a recording comes back from the speech engine without them |
srt, vtt | subtitle files as text |
language | detected language code, like en |
durationSeconds, wordCount | length of the recording and number of words |
speech | false when the recording has no speech |
title, author, publishedAt, url | episode or video data, when the source has it |
inputUrl, sourceType | the link you gave and what it turned out to be |
transcriptSource, transcriptFormat | publisher when the podcast's own transcript was used, youtube-captions when the YouTube video's author captions were used, and the format (vtt, srt, json, html, plain) |
translatedText, translatedSegments, translatedSrt, translatedVtt, translationLanguage, translationStatus | with Translate to: the first language |
translations, translationFailedLanguages | with two or more languages: for each language code (the first one too) its status (ok, same_language or error), text, and srt and vtt when the transcript has timestamps and subtitles are on; and the languages that failed |
speakerCount, speakerTranscript | with the speaker option: how many voices (for a recording labelled in one pass), and the dialogue as Speaker 1: ... lines |
summary, chapters, keyPoints, keywords, speakersNamed | with the summary option |
chargedMinutes, status, error | what was charged, and why a link failed |
mentions, mentionCounts | with Find mentions of: each mention with term, start, end, text (the phrase around it), speaker and link, and the number per term |
trimmedFields | only on a row that was over Apify's 9 MB limit: the fields left out |
{"inputUrl": "https://archive.org/download/gettysburg_johng_librivox/gettysburg_address_64kb.mp3","sourceType": "file","title": "gettysburg_address_64kb.mp3","durationSeconds": 157.9,"language": "en","speech": true,"wordCount": 304,"text": "This is a LibriVox recording. All LibriVox recordings are in the public domain. ... The Gettysburg Address... by Abraham Lincoln. November 19th 1863 Four score and seven years ago our fathers brought forth on this continent a new nation, ...","segments": [{"start": 0.33, "end": 1.93, "text": "This is a LibriVox recording."},{"start": 2.43, "end": 4.85, "text": "All LibriVox recordings are in the public domain."}],"srt": "1\n00:00:00,330 --> 00:00:01,930\nThis is a LibriVox recording.\n\n2\n...","summary": "The Gettysburg Address is a historic speech delivered by Abraham Lincoln during the American Civil War at the dedication of the Soldiers' National Cemetery. ...","chapters": [{"start": 0, "title": "Introduction and Historical Context"},{"start": 65, "title": "Honoring the Fallen and the Call to Action"}],"keywords": ["Gettysburg Address", "Abraham Lincoln", "Civil War", "Liberty", "Equality"],"chargedMinutes": 3,"status": "ok"}
A real row from a test run, shortened.
How to use it
- Paste links into Media links, one per line.
- For podcast feeds and channels, set Episodes per podcast feed or channel (3 by default).
- Turn on Speaker labels, set Translate to, or turn on Summary, chapters and key points if you need them.
- Run, then export to JSON, CSV or Excel, or connect via API, Make, Zapier or n8n.
Which links work
| Link | Example | What is transcribed |
|---|---|---|
| Audio or video file | https://example.com/episode.mp3 | the file: mp3, m4a, wav, ogg, flac, mp4, mov, webm and more |
| Google Drive or Dropbox file | a share link, https://drive.google.com/file/d/... or https://www.dropbox.com/scl/fi/... | the file, when it is shared with anyone who has the link |
| Podcast RSS feed | https://feeds.megaphone.fm/hubermanlab | the newest episodes |
| Apple Podcasts show | https://podcasts.apple.com/us/podcast/the-daily/id1200361736 | the newest episodes, from the show's feed |
| Apple Podcasts episode | a link with ?i= | that episode |
| YouTube video | https://www.youtube.com/watch?v=..., youtu.be/..., Shorts, a past live stream | the video's audio |
| YouTube channel | https://www.youtube.com/@TED | the channel's newest videos |
| YouTube playlist | https://www.youtube.com/playlist?list=... | the first videos of the playlist |
| Video page | TikTok, Instagram, Facebook, SoundCloud, Dailymotion | the video's audio |
Other video sites often work too. A link that fails is not charged. A SoundCloud artist link gives
the artist's newest tracks; TikTok profile links are not supported. A YouTube video link with
&list= is one video, not the playlist.
Not supported: Vimeo (needs a login), age-restricted and members-only YouTube videos,
Spotify (audio is DRM protected; use the show's RSS feed or Apple Podcasts link instead), private
or login-only videos, and live streams that have not ended. These come back as rows with
status: "error" and are not charged.
Only new episodes, on a schedule
- Put a podcast feed, Apple Podcasts show or YouTube channel link into Media links and set Episodes per podcast feed or channel, for example 3.
- Turn on Only new episodes and give the schedule a List name, for example
my-podcast. - Save the input as a task and add it to an Apify schedule, for example daily.
The first run transcribes the newest episodes and remembers them. Each later run reads up to 500
newest episodes of the feed (60 newest videos of a YouTube channel) and takes every episode
published since the newest one it remembers, however many came out; episodes on the list are not transcribed, not charged and not added to the
dataset. A YouTube playlist is not watched this way: each run looks at its first videos only, so
videos added at the end of a playlist are not picked up; use the channel link instead. A recording that failed is not remembered and is tried again while it is among the newest
episodes. The list is kept in a key-value store named audio-video-transcription-monitor in your
account, in the record seen-<list name>; delete the record to start over. Runs with different list
names do not see each other's lists. Do not start two runs with the same list name at the same time:
both would transcribe the same new episode.
If you start runs with a scoped API token (Make, n8n, your own code), the token needs permission to create, read and write key-value stores.
Published after takes only feed episodes and channel videos from a date (2026-09-01) or a
window back from now (30 days, 2 weeks). Episodes without a date in the feed are kept. YouTube
gives channel videos an approximate date ("3 days ago"), so a video near the boundary can fall on
either side of it.
Only some episodes, by title
Episode title contains keeps only episodes whose title contains one of the texts, for example
interview; Episode title does not contain skips episodes with trailer, rerun or best of
in the title. Both work on podcast feeds, Apple Podcasts shows, YouTube channels and playlists and
SoundCloud artist links. Put one text per line; a comma is part of the text, so interview, Q&A in
one line looks for exactly that. A text is found anywhere in the title, also inside words (ad also
matches "Bad news", so prefer whole words like ad break). Case and accents are ignored (cafe
keeps Café), and * matches anything (interview*ceo keeps "Interview with the CEO"). Episodes per podcast feed or channel
counts only episodes that pass: with 3 and interview, you get the 3 newest interviews, not the
interviews among the 3 newest episodes. Skipped episodes are not charged, not added to the dataset
and not remembered by Only new episodes. A YouTube channel or playlist is searched among at least
its 200 newest (first) videos, a SoundCloud artist among at least 200 tracks. A site that lists
recordings without titles gives an error row for that link instead of an empty result. A direct link to one episode or video is never filtered.
Find mentions of brands and topics
Put terms in Find mentions of, one per line (or several in one line, separated by a comma and a space). Input:
{"urls": ["https://feeds.megaphone.fm/darknetdiaries", "https://www.youtube.com/watch?v=jNQXAC9IVRw"],"maxEpisodesPerFeed": 1, "searchTerms": ["FBI", "hack*", "elephants", "password"]}
Each row gets the mentions in that recording. The YouTube row of a test run (17 October 2026):
"mentions": [{"term": "elephants", "start": 0, "end": 4,"text": "Alright, so here we are, one of the elephants.","link": "https://www.youtube.com/watch?v=jNQXAC9IVRw&t=0s"}],"mentionCounts": {"FBI": 0, "hack*": 0, "elephants": 1, "password": 0}
The podcast episode of the same run got {"FBI": 1, "hack*": 35, "elephants": 0, "password": 2},
each mention with a link to the episode's audio file at that second, like ...mp3#t=143, and the
run's MENTIONS record had the totals: {"FBI": 1, "hack*": 35, "elephants": 1, "password": 2}.
textis the phrase around the mention: the line of the transcript, or up to 150 characters on each side when the line is longer.linkopens the recording at that second: a YouTube video (Shorts too) as a normal watch link with the time, other recordings as a link to the audio file itself with#t=and the second, which browser players understand. A video page (TikTok, Instagram and others) and a podcast transcript without timestamps give mentions without a link; the latter also without time.- Case is ignored, and so are accents on Latin letters (
cafefindsCafé);еfindsё. Other marks stay, because they change the letter:мойdoes not findмои,パンdoes not findバン. - Whole words are matched:
apifydoes not findapifying,apif*does;*works anywhere in a word. A number is not found inside a bigger one (100does not find1,100or100,000). In Chinese, Japanese and Korean a term is found anywhere in the text. - A term of several words is found also when it runs over several lines of the transcript.
- Up to 50 terms. Search runs on the finished transcript, so it costs nothing extra and works on transcribed recordings, podcast transcripts from feeds and YouTube videos.
The run's key-value store has MENTIONS with the totals per term for the whole run, and
MENTIONS.csv (UTF-8 with BOM, opens in Excel) with the mentions of the run, up to 20,000. A row
lists up to 2,000 mentions (mentionsTruncated: true when there were more, and only those go to
the CSV); mentionCounts always has the full numbers.
Transcribe a file from your computer
Put the file in Google Drive or Dropbox, share it, and paste the share link into Media links:
- Google Drive: right-click the file, Share, set General access to Anyone with the link, then Copy link.
- Dropbox: Share, Copy link, and paste the whole link, including the
rlkey=part.
A file that is not shared comes back as an uncharged row saying how to share it. The actor does not read files from your Apify storage: it runs with limited permissions and cannot open them.
Chain it after another actor
Put the dataset ID of a finished run of a podcast, TikTok or video scraper into Dataset ID, or
pass its rows as datasetItems. In each row the actor takes the first field that holds a link:
audioUrl, mediaUrl, videoUrl, episodeUrl, url, link and similar. With the "Connect
actor" integration put {{resource.defaultDatasetId}} into datasetId. One run reads up to
10,000 rows.
Input fields of other transcription actors are read too
If your API calls were built for another transcription actor, you can send the same input. Links
are read from urls, mediaUrls, audioUrls, podcastUrls, podcastFeeds, sources,
media_urls, feed_urls and episode_urls, as strings or {"url": ...} objects. maxEpisodesPerShow, episodesPerFeed and rss_episodes set episodes
per feed; maxMinutesPerFile and maxDurationMinutes set the per-recording limit;
outputFormats without srt and vtt turns subtitles off; speakerLabels and diarize turn
speaker labels on; translateToEnglish: true works like Translate to en; a list of languages in
subtitleLanguages or targetLanguages works like Translate to (in Translate to itself,
separate languages with commas);
usePublisherTranscripts: false always transcribes the audio; aiInsights and generateChapters turn the summary on. newItemsOnly and
newEpisodesOnly turn on only new episodes, with
watchlistId as the list name; episodesSince and published_after work like Published after.
includeWords and word_timestamps work like Word timestamps. Vocabulary hints (vocabulary,
vocabularyHint, keyterms, initialPrompt) are accepted but ignored: the speech engine does not
take them. episodeTitleContains (alternatives separated by |), titleContains and title_contains work like
Episode title contains; episodeTitleExcludes and title_excludes like Episode title does not
contain. The output fields are this actor's own (see above).
Pricing
| Event | Price |
|---|---|
| Audio minute transcribed | $0.005 per started minute of a recording with speech; $0.0045 on the Business plan and higher (Apify's GOLD discount tier and above) |
| Speaker labels | $0.003 per started minute, only with the speaker option and only when the labels were made |
| Translation | $0.002 per started minute of the recording for each language, only with Translate to and only for languages that were translated |
| AI summary and chapters | $0.01 per started hour of a recording, only with the summary option |
Examples: a 30-minute podcast episode costs $0.15, $0.24 with speaker labels, or $0.27 translated into Spanish and German; a 3-hour one $0.90 ($0.81 on Business and higher); a 20-second TikTok $0.005. Apify's $5 free credit covers about 1,000 audio minutes. The other events cost the same on every plan.
Not charged: audio minutes of episodes with the podcast's own transcript and of YouTube videos with their author's captions, recordings without speech, links that fail or are not supported, duplicates in one run, summaries and translations that fail (a failed language is named in the row; the other languages are still charged), and translation of a recording into its own language (when the language is known: a podcast transcript from a feed without a language tag is translated and charged for every language you set).
Cap your spending: set the run's maximum cost, Max minutes per run, or Max minutes per
recording. With translation into two or more languages, a recording counts toward Max minutes
per run once per language; translated minutes of podcast transcripts count too. The actor checks the limit before each recording and does not start one that would go
over it; that row says status: "skipped".
Good to know
-
The podcast's own transcript. When the feed lists one for an episode, the actor takes it in the best format offered: VTT or SRT (with timestamps, and speaker names when the transcript has them), Podcasting 2.0 JSON, then HTML or plain text (text only, no timestamps or subtitles). It is the publisher's text, not ours; turn off Use the podcast's or video's own transcript to always transcribe the audio. With speaker labels on, the audio is always transcribed. The podcast's transcript has no word timestamps (
wordsIncomplete: true); turn it off to get them. In a test on 16 podcast feeds, 6 had transcripts (Talk Python, Darknet Diaries, Changelog and a Buzzsprout show for all or most episodes, Radio Ambulante and Acquired for some); the biggest shows tested (Lex Fridman, Huberman Lab, The Daily) had none. -
Translation is made from the finished transcript by GPT-6 Luna through OpenRouter, in batches of lines, so each translated line keeps its timestamps and speaker. Tested Spanish to English and English to Russian; 15 minutes of speech took about 20 to 50 seconds to translate. A podcast transcript without timestamps (HTML or text) is translated by paragraphs and gets no translated subtitles. Several languages are translated at the same time, two at once; a language given twice (
esandSpanish) is translated once, regional variants are one language (pt-BRandpt-PTgive Portuguese,zhis Simplified Chinese), and languages after the fifth are skipped with a warning in the log. A row over Apify's 9 MB limit (five translations of a recording of about five hours or more) leaves out repeated data first: the copy of the first language intranslations, then VTT subtitles, segments and SRT subtitles, and names what was left out intrimmedFields. Translated text is kept; if even that does not fit, the last languages are left out, named intranslationFailedLanguagesand not charged. -
Speech is transcribed by Whisper large-v3 turbo. When it returns nothing on a part that has sound, a second model checks that part. With speaker labels it is transcribed by ElevenLabs Scribe v2, which also tells the voices apart; if Scribe fails, the recording is transcribed by Whisper without labels, and the labels are not charged (the row says
speakerError). -
YouTube author captions. When the video's author uploaded captions in the language of the video, the row is made from them: text, timestamps and subtitles,
, no audio minutes charged. YouTube's automatic captions are not used (they have no punctuation), and neither are captions in another language (those are translations). When YouTube does not say the video's language, or the captions are far too short for the video, the audio is transcribed as usual. The captions are the author's text, sound notes like "(Applause)" included; turn off Use the podcast's or video's own transcript to always transcribe. With speaker labels on, the audio is transcribed. Summary, translation and mentions work as with a podcast's own transcript. In a test of 10 videos (TED talks and tech reviews) on 18 October 2026, 7 came back from author captions in 3 to 5 seconds each; the other 3 were transcribed.transcriptSource: "youtube-captions" -
A recording is transcribed up to 600 minutes, or up to Max minutes per recording; a longer one is transcribed from the start up to the limit and the row says
truncated: true. A YouTube video longer than 10 hours is not downloaded at all and comes back as an uncharged row, unless it has author captions (then the captions are used up to the same limit). -
File size: up to about 500 MB per file at the default 1 GB memory. The run's disk grows with its memory, so give the run more memory for bigger video files (2 GB at most). A podcast episode is usually 30 to 200 MB.
-
YouTube refuses downloads from cloud servers such as Apify's (in our test 1 video out of 20 came through), so YouTube audio is downloaded by our own server and passed to the run. The server gets only the YouTube link over an encrypted connection, keeps the audio only until the run has received it, does not log links, and downloads one video at a time. When YouTube slows it down, those videos come back as uncharged rows that say to run again later.
-
The audio is sent to a speech recognition service (Whisper, or ElevenLabs Scribe with speaker labels, through OpenRouter) to be transcribed. With Translate to the transcript text is sent to an AI model (GPT-6 Luna, or Gemini when Luna fails, through OpenRouter) to be translated. With the summary option the transcript text is also sent to an AI model (Gemini through OpenRouter). Nothing else from your account is sent.
-
Timestamps are in seconds from the start of the recording. Pieces are split at pauses, so a sentence is rarely cut in two.
-
The language is detected for every 10-minute piece, so an English ad at the start of a Spanish episode does not turn the episode into English.
languageis the language of most of the speech. Set Language only if detection gets it wrong. -
Speaker labels are numbers, not names: Speaker 1 is the first voice heard. With the summary option,
speakersNamedlists the people the speakers name. A recording up to about 3.3 hours is labelled in one pass; a longer one in parts of up to 3.3 hours, numbered separately in each part (Speaker 1 (part 2) and so on, the row says so inspeakerNote). A line is now and then given to the wrong voice, and Scribe writes numbers as words ("eighteen sixty-three"). -
In test runs speaker labels were right on an 18-minute two-person interview, told apart the host, the reporter, the guest and the ad voice on a 30-minute news podcast, and labelled a 3.3-hour interview as two voices in one pass.
-
The default run memory is 1 GB. In test runs a 3.6-hour episode took 9 minutes from start to finish, and files of 2 to 18 minutes took 10 to 20 seconds.
-
A run times out after 2 hours by default. For a big batch, such as a whole podcast back catalogue, raise the run timeout in the run options or split the batch.
FAQ
Can I transcribe a whole podcast? Yes. Put its RSS feed or Apple Podcasts show link in Media links and set Episodes per podcast feed or channel, up to 500. Long back catalogues take time (a 3.6-hour episode is about 9 minutes), so raise the run timeout for big batches.
Why did my YouTube link fail? The row's error says why. Private, removed, age-restricted
and members-only videos cannot be downloaded without an account, and this actor does not use
yours. Live streams work after they end. When YouTube pauses our downloader for a few minutes, the
row says to run again later. Failed YouTube links are not charged.
Is my file stored? Files are downloaded into the run's temporary storage and deleted after the transcript is made. Only the transcript is saved, to your dataset. With Only new episodes the run also keeps a list of short hashes of the recordings it transcribed, in your account.
Found a bug or need a field? Open an issue on the Issues tab.