# Video Transcript Scraper: TikTok, Instagram, YouTube & X (`scrape-lads/video-transcript-scraper`) Actor

Get transcripts from TikTok, Instagram Reels, YouTube videos and Shorts, and X videos. Native subtitles first, Whisper speech-to-text when a video has none. Timestamped segments, language, author, caption and stats. Pay only for transcripts.

- **URL**: https://apify.com/scrape-lads/video-transcript-scraper.md
- **Developed by:** [Scrape Lads](https://apify.com/scrape-lads) (community)
- **Categories:** Videos, Social media, AI
- **Stats:** 2 total users, 2 monthly users, 100.0% runs succeeded, 1 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.00 / 1,000 transcript from subtitles

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

### What does Video Transcript Scraper do?

**Video Transcript Scraper turns TikTok, Instagram Reels, YouTube videos and Shorts, and X (Twitter) videos into clean text transcripts with timestamps.** Paste video links, or a creator's profile to get their latest videos, and get one row per video. Each row has the full transcript, timestamped segments, the detected language, the author, caption, duration and engagement stats.

It reads the platform's **own subtitles first** (TikTok's captions and YouTube's captions), which are fast and cheap. When a video has none (every Instagram Reel, X videos, and TikToks without captions), it **transcribes the audio with Whisper speech-to-text**. Every row says which method was used.

Run it in Apify Console, call it from the **API**, **schedule** it, or connect it to Make, Zapier, n8n, Google Sheets or your own code. Apify takes care of proxies, retries and monitoring.

### Why use this video transcript scraper?

- **One actor for four platforms.** You get a TikTok transcript, an Instagram transcript, a YouTube transcript and an X video transcript in the same format, with no extra tools.
- **Reels transcript without subtitles.** Instagram doesn't publish captions, so most tools give up. This one transcribes the speech.
- **Cheap when subtitles exist.** Native subtitles cost less than speech-to-text, and you only pay for speech-to-text when it is actually needed.
- **Pay only for transcripts.** Private, deleted or silent videos are free.

Common uses:

- **AI and RAG:** feed creator videos into a knowledge base or a GPT, or summarize them.
- **Content research:** see what top creators actually say in their hooks, scripts and calls to action.
- **Repurposing:** turn short videos into blog posts, newsletters and captions.
- **Brand and ad monitoring:** search spoken mentions of products, competitors or claims.
- **Accessibility and translation:** start subtitles or translations from an accurate transcript.

#### TikTok transcript, Instagram transcript, YouTube transcript and X video transcript

All four platforms come back in the same row format. TikTok and YouTube use their own captions when they exist. An Instagram Reels transcript and an X video transcript always come from speech-to-text, because those platforms publish no subtitles.

### How to get transcripts from TikTok, Instagram, YouTube and X

1. Click **Try for free** and open the **Input** tab.
2. Paste video URLs into **Video URLs**, or creators into **Profiles or channels**, and set how many of the latest videos to take.
3. Leave **Speech-to-text** on "Fallback" (recommended), or pick "Never" for subtitles only.
4. Click **Start**. A few videos take seconds.
5. Download the results as **JSON, CSV, Excel or HTML**, or read them through the API.

### Input

Everything is set on the **Input** tab. Example:

```json
{
    "urls": [
        "https://www.tiktok.com/@garyvee/video/7696603359335288078",
        "https://www.instagram.com/reel/Dd-VQPnRz0t/",
        "https://www.youtube.com/shorts/aNI2jv7lBPQ",
        "https://x.com/elonmusk/status/1585341984679469056"
    ],
    "profiles": ["https://www.tiktok.com/@garyvee", "https://www.youtube.com/@MrBeast/shorts"],
    "maxVideosPerProfile": 10,
    "speechToText": "fallback",
    "language": "",
    "includeSegments": true
}
```

| Field | What it does |
| --- | --- |
| `urls` | Video links. Accepted: TikTok videos and short links, Instagram Reels and video posts, YouTube videos, Shorts and youtu.be links, and X/Twitter posts with a video. |
| `profiles` | Creators whose latest videos you want: `tiktok.com/@name`, `instagram.com/name`, `youtube.com/@channel` (add `/shorts` for the Shorts tab). |
| `maxVideosPerProfile` | How many of the newest videos to take per profile (Instagram serves at most 12 without a login). |
| `speechToText` | `fallback` (subtitles first, speech-to-text when there are none), `always`, or `never`. |
| `language` | Optional two-letter code. Picks the matching subtitle track and tells Whisper which language is spoken. |
| `includeSegments` | Include the timestamped segments (on by default). |
| `maxSpeechToTextSec` | Longest video sent to speech-to-text (default 1,800 s). |

### Output

One row per video. You can download the dataset in various formats such as JSON, HTML, CSV, or Excel.

```json
{
    "url": "https://www.instagram.com/reel/Dd-VQPnRz0t/",
    "platform": "instagram",
    "status": "success",
    "author": "feelgoodfoodie",
    "caption": "As soon is fall rolls around, I love to start roasting spaghetti squash...",
    "durationSec": 30,
    "language": "en",
    "transcript": "If you want an easier way to cut spaghetti squash, microwave it first for three minutes. Then it's so much easier to cut in half...",
    "segments": [
        { "start": 0, "end": 2.5, "text": "If you want an easier way to cut spaghetti squash," },
        { "start": 2.5, "end": 4.4, "text": "microwave it first for three minutes." }
    ],
    "wordCount": 100,
    "transcriptSource": "speech-to-text",
    "subtitleKind": null,
    "stats": { "views": 171362, "likes": 2831, "comments": 357, "shares": null },
    "fromProfile": null,
    "errorCode": null,
    "charged": true
}
```

The Output tab has three views: **Transcripts**, **Videos and stats**, and **Status per URL**.

### Data fields

| Field | Description |
| --- | --- |
| `url`, `platform`, `videoId` | The video and where it lives (`tiktok`, `instagram`, `youtube`, `x`). |
| `author`, `authorName`, `authorUrl` | Creator handle, display name and profile link. |
| `title`, `caption` | YouTube title, or the post caption or description. |
| `durationSec`, `publishedAt`, `thumbnailUrl` | Video length, publish date (when available), cover image. |
| `transcript` | Full transcript as one text. |
| `segments` | `{ start, end, text }` with times in seconds. |
| `language` | Two-letter language of the transcript. |
| `transcriptSource` | `subtitles` (platform captions) or `speech-to-text` (Whisper). |
| `subtitleKind` | `creator` (written by the creator) or `auto` (platform speech recognition). |
| `stats` | Views, likes, comments and shares, when the platform shows them. |
| `wordCount`, `fromProfile` | Transcript length; the profile the video came from. |
| `status`, `errorCode`, `message` | `success`, `no_transcript` or `failed`, with a reason such as `private_or_removed`, `no_speech` or `too_long`. |
| `charged` | Whether this row was billed. |

### How much does it cost to get video transcripts?

Pay per result, with no subscription:

- **$2 per 1,000 subtitle transcripts** (TikTok and YouTube videos that have captions).
- **$5 per 1,000 speech-to-text transcripts** (Instagram Reels, X videos, and videos without captions), covering the first minute of audio. Longer videos add $0.0025 per extra started minute (a 3-minute video costs $0.01).
- A small $0.005 start fee per run.

**Failed, private, removed and silent videos are free.** Example: 1,000 TikTok transcripts plus 1,000 Instagram Reels under a minute cost about $7. The free Apify plan's monthly credit covers hundreds of transcripts.

### Tips

- Use **Fallback** mode. TikTok and YouTube captions are the cheapest and most accurate source, and speech-to-text fills the gaps.
- Choose **Never** to get subtitles only. Videos without them come back free with `no_subtitles`.
- Set **Language** when you need a specific subtitle track (for example `es`), or to help Whisper with a less common language.
- Turn off **Include timestamped segments** if you only need the plain text.
- Lower **Longest video for speech-to-text** to stop long uploads from adding extra-minute charges.

### FAQ, limits and support

**Is it legal to scrape video transcripts?** The actor only reads public videos that anyone can watch without logging in. You are responsible for how you use the data: respect copyright, platform terms and privacy laws such as the GDPR, and don't republish creators' content without permission.

**Which videos can't be transcribed?** Private or deleted videos, age-restricted posts, and Instagram posts with embedding turned off. YouTube videos without captions can only be transcribed when they are very short, because YouTube doesn't serve the full audio to logged-out players. Music-only videos come back as `no_speech` and are free.

**How accurate is speech-to-text?** It uses Whisper large-v3 turbo, which handles 90+ languages and is very accurate on clear speech. Background music and heavy slang lower accuracy.

**Facebook videos?** Not supported yet. Open an Issue if you need them.

Found a problem or need a field? Open an **Issue** on the actor page. We fix things fast. For a custom pipeline, such as transcripts sent straight into your database or an AI summary per video, get in touch through the Issues tab.

# Actor input Schema

## `urls` (type: `array`):

TikTok videos, Instagram Reels and video posts, YouTube videos and Shorts, and X (Twitter) posts with a video. Short links (vm.tiktok.com, youtu.be) work too. One transcript row per video. Provide video URLs, profiles below, or both.

## `profiles` (type: `array`):

Get transcripts for the latest videos of a creator: tiktok.com/@name, instagram.com/name, youtube.com/@channel (add /shorts for the Shorts tab). Instagram serves at most the 12 newest posts without a login.

## `maxVideosPerProfile` (type: `integer`):

How many of the newest videos to transcribe from each profile or channel.

## `speechToText` (type: `string`):

When to transcribe the audio with Whisper. 'Fallback' uses the platform's own subtitles when a video has them (TikTok, YouTube) and speech-to-text otherwise (always for Instagram and X). 'Always' transcribes the audio even when subtitles exist. 'Never' returns subtitles only, so videos without them are skipped for free.

## `language` (type: `string`):

Two-letter language code such as en, es or fr. Picks the subtitle track in that language when a video has several, and tells speech-to-text which language is spoken. Leave empty to detect it automatically.

## `includeSegments` (type: `boolean`):

Add the transcript split into segments with start and end times in seconds. Turn off to get the plain text only.

## `maxSpeechToTextSec` (type: `integer`):

Videos longer than this are not sent to speech-to-text (they still get subtitles when they have them). Protects you from paying for a 3 hour livestream by mistake.

## `maxConcurrency` (type: `integer`):

How many videos are processed at the same time.

## Actor input object example

```json
{
  "urls": [
    "https://www.youtube.com/watch?v=jNQXAC9IVRw",
    "https://www.instagram.com/reel/Dd-VQPnRz0t/"
  ],
  "maxVideosPerProfile": 10,
  "speechToText": "fallback",
  "includeSegments": true,
  "maxSpeechToTextSec": 1800,
  "maxConcurrency": 5
}
```

# Actor output Schema

## `transcripts` (type: `string`):

No description

## `fullResults` (type: `string`):

No description

## `runSummary` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "urls": [
        "https://www.youtube.com/watch?v=jNQXAC9IVRw",
        "https://www.instagram.com/reel/Dd-VQPnRz0t/"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("scrape-lads/video-transcript-scraper").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = { "urls": [
        "https://www.youtube.com/watch?v=jNQXAC9IVRw",
        "https://www.instagram.com/reel/Dd-VQPnRz0t/",
    ] }

# Run the Actor and wait for it to finish
run = client.actor("scrape-lads/video-transcript-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "urls": [
    "https://www.youtube.com/watch?v=jNQXAC9IVRw",
    "https://www.instagram.com/reel/Dd-VQPnRz0t/"
  ]
}' |
apify call scrape-lads/video-transcript-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,scrape-lads/video-transcript-scraper"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/8cadcXefwZDJFQHe3/builds/ta8WXzsEYeU3ZVbRe/openapi.json
