# YouTube Video Comments Scraper – Text & Authors (`scrapingmonkey/youtube-video-comments-scraper`) Actor

Collect public YouTube video comments with text, authors, likes, reply counts, and source-video context. Set a page budget and export one row per comment.

- **URL**: https://apify.com/scrapingmonkey/youtube-video-comments-scraper.md
- **Developed by:** [ScrapingMonkey](https://apify.com/scrapingmonkey) (community)
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.00 / 1,000 results

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

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

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
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.
Actors are written with capital "A".

## 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.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

Collect the public discussion under known YouTube videos, with each comment saved as an individual record. **YouTube Video Comments Scraper** returns text, authors, published-time labels, likes, reply counts, and visible pinned or creator-heart indicators.

Use it to research audience feedback, compare reactions to selected videos, or build a comment dataset for repeated analysis. Every row keeps the source video's ID and available context.

| At a glance | Details |
|---|---|
| 📥 Input | Full YouTube video URLs |
| 📤 Output | Comment text, authors, likes, reply context, and source-video details |
| 🔐 Login required | No YouTube credentials or cookies |
| ⚡ Processing | Up to 5 requests concurrently with automatic retries |
| 💾 Delivery | One row per collected comment; visible embedded replies can also become rows |

### What the YouTube video comments scraper extracts 🔎

The Actor opens each video's public comment collection and follows its available comment pages. Fields can include:

- Comment ID, permalink, text, and published-time label
- Like count and its source label, plus available reply count and level
- Author channel ID, name, handle, URL, avatars, and account indicators
- Pinned text and creator-heart information when exposed
- Links and channel mentions found in the comment
- Available parent-comment ID for replies included in the response
- Video ID, source-video title, channel, author, and views when supplied
- The visible comment total and the result's collection position

### How to scrape YouTube video comments 🚀

1. Add full video URLs to `inputList`.
2. Choose `pagesPerInput` for the comment-page budget per video.
3. Start the Actor and review comment rows and failed results.
4. Export the dataset or group comments by `video_id` for analysis.

```json
{
  "inputList": [
    "https://www.youtube.com/watch?v=jNQXAC9IVRw"
  ],
  "pagesPerInput": 2
}
```

### YouTube video comments data fields and output 📦

| Field group | Included data |
|---|---|
| Comment | ID, URL, text, published-time label, likes, and reply count |
| Author | Channel identity, handle, profile link, avatar variants, and visible account indicators |
| Discussion context | Parent ID, reply level, pinned or hearted indicators, links, and mentions |
| Source video | Video identity, title, channel, author, available views, and comment total |
| Collection | Original input, success or failed status, and position within that input |

Complete illustrative success item. The content and values below are fictional examples, not a live result:

```json
{
  "input": "https://www.youtube.com/watch?v=TrailWalk01x",
  "status": "success",
  "id": "UgExampleThread01",
  "url": "https://www.youtube.com/watch?v=TrailWalk01x&lc=UgExampleThread01",
  "parent_comment_id": null,
  "text": "Which section has the most shade?",
  "published_text": "1 day ago",
  "likes": 7,
  "likes_text": "7",
  "replies_count": 2,
  "reply_level": 0,
  "is_pinned": false,
  "pinned_text": null,
  "is_hearted": false,
  "hearted_by": null,
  "creator_thumbnail": null,
  "is_liked": null,
  "author.id": "UCaaaaaaaaaaaaaaaaaaaaaa",
  "author.name": "Maya Park",
  "author.handle": "@trailjournal",
  "author.url": "https://www.youtube.com/@trailjournal",
  "author.avatar_url": "https://example.com/maya-avatar.jpg",
  "author.avatar_thumbnails.url": [
    "https://example.com/maya-avatar-small.jpg",
    "https://example.com/maya-avatar.jpg"
  ],
  "author.avatar_thumbnails.width": [
    80,
    160
  ],
  "author.avatar_thumbnails.height": [
    80,
    160
  ],
  "author.is_verified": false,
  "author.is_creator": false,
  "author.is_artist": null,
  "author.is_current_user": null,
  "links.text": [],
  "links.url": [],
  "mentions.channel_id": [],
  "mentions.name": [],
  "mentions.url": [],
  "comments_total": 18,
  "video_id": "TrailWalk01x",
  "source_video.id": "TrailWalk01x",
  "source_video.url": "https://www.youtube.com/watch?v=TrailWalk01x",
  "source_video.title": "A forest walk in three stops",
  "source_video.channel_id": "UCaaaaaaaaaaaaaaaaaaaaaa",
  "source_video.author": "Trail Journal",
  "source_video.views": 12400,
  "position": 1
}
```

Each comment is one row in one table, with the same literal dotted field names in JSON. Author-avatar, link, and mention columns align by position within their groups. Source-video details stay in the comment row. `position` is collection order, not a relevance score or a permanent YouTube rank.

Missing optional fields can be `null`, empty strings, or empty lists. Some flags default to `false` when no signal is present. A failed row retains `input`, sets `status` to `failed`, and leaves the result-data fields null.

### Input requirements and coverage ⚙️

| Parameter | Type | Default | Rules |
|---|---|---|---|
| `inputList` | array of strings | Required | At least one full supported YouTube video URL. Bare video IDs are not accepted. |
| `pagesPerInput` | integer | `1` | Minimum 1, with no fixed upper limit. Limits result pages for each input; YouTube controls page size. |

Accepted video forms include watch URLs, youtu.be links, and supported /shorts/, /live/, /embed/, or /v/ URLs. Bare video IDs, channel links, and playlist-only links are not accepted.

The Actor paginates the video's comment collection. Replies already present in those responses can be saved as rows, but their individual reply threads are not separately paginated. Use Comment Replies Scraper to target the replies to a known top-level video comment.

There is no sorting input. The dataset follows the public collection order YouTube returns, which can change between runs.

Each input has its own collection order and duplicate tracking. Repeated results within that input are skipped; the same result may appear again under another input. Repeated input entries are processed separately.

The page budget counts result pages. Requests needed to open the collection do not consume it. Collection ends at the budget or when YouTube stops providing a usable next page. If collection ends without any results, the Actor saves a failed row for that input. An empty end after saved results does not add a failure.

### YouTube video comment use cases 🎯

#### Audience-feedback research

Collect public questions, reactions, and requests from selected videos while retaining their source context.

#### Content comparisons

Compare comment text, likes, and visible discussion indicators across a defined video sample.

#### Discussion triage

Use comment links and available reply counts to select threads for focused reply collection or manual review.

#### Repeated comment collection

Compare comment IDs with previously saved results to identify newly observed discussion in your own database.

### Pricing and billable comment rows 💰

Check the Actor's **Pricing** tab for the current charging model and rate.

Under dataset-item pricing, each saved success or failed row can be billable. Automatic retries do not independently create extra rows. Repeated input entries can produce repeated billable results.

A visible reply saved as a row counts as a comment result under dataset-item pricing. Author images and source-video details remain within the row. The page budget does not guarantee a particular number of comments.

### YouTube Video Comments Scraper API and integrations 🔌

Use the Actor ID from the **API** tab as `$ACTOR_ID` and your Apify token as `$APIFY_TOKEN`.

```bash
curl -X POST "https://api.apify.com/v2/acts/$ACTOR_ID/runs?token=$APIFY_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"inputList":["https://www.youtube.com/watch?v=jNQXAC9IVRw"],"pagesPerInput":2}'
```

This request starts a run. Retrieve the default dataset after completion, or use schedules and webhooks to connect it to a recurring workflow. Export JSON, CSV, or Excel, or send selected fields to Google Sheets, Make, Zapier, or your own application.

### Reliability and limits ⚠️

Temporary request failures are retried. Invalid or unavailable targets produce failed rows while other inputs can continue. A later-page failure can add a failed row alongside results already saved for the same input.

Comments may be disabled, restricted, deleted, or unavailable even when a video remains public. Public comment totals and reply counts can exceed the rows collected within your page budget.

Like counts may be parsed from abbreviated labels; retain `likes_text` when precision matters. Published times are the source's text labels, not exact timestamps. Pinned, hearted, and author indicators can be missing or defaulted.

### Frequently asked questions ❓

#### Does it collect every reply?

It saves replies already included in the requested comment pages. It does not separately paginate every reply thread; use Comment Replies Scraper for a selected top-level comment.

#### How many comments are in one page?

YouTube controls page size. The page budget limits comment-result pages rather than an exact number of rows.

#### Can I choose newest or top comments?

There is no sorting parameter. Results follow the public comment collection YouTube returns.

#### Why does a public video produce a failed result?

Its comments may be disabled or unavailable, the required public collection may be inaccessible, or collection may end without usable results.

#### Are repeated video URLs processed once?

No. Repeated inputs are processed separately. Remove repeated entries before running if you want to avoid duplicate collections.

#### Does the output include exact comment timestamps?

It preserves YouTube's published-time text, such as a relative date label, rather than supplying an exact timestamp.

### Support, responsible use, and related actors 🛟

For a reproducible issue, share the run ID, a safe public input, and the field or behavior you expected through the Actor's support channel. Keep tokens and other credentials out of support messages.

Use public content in accordance with applicable privacy, copyright, contractual, and platform requirements.

# Actor input Schema

## `inputList` (type: `array`):

Add full YouTube video URLs, one per item. Raw video IDs are not accepted.

## `pagesPerInput` (type: `integer`):

Number of result pages to collect for each input. YouTube controls the page size. Results are saved after each page; collection stops when the list ends. Bootstrap requests do not count as result pages.

## Actor input object example

```json
{
  "inputList": [
    "https://www.youtube.com/watch?v=jNQXAC9IVRw"
  ],
  "pagesPerInput": 1
}
```

# Actor output Schema

## `results` (type: `string`):

Success and failed rows. Check the status column.

# 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 = {
    "inputList": [
        "https://www.youtube.com/watch?v=jNQXAC9IVRw"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("scrapingmonkey/youtube-video-comments-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 = { "inputList": ["https://www.youtube.com/watch?v=jNQXAC9IVRw"] }

# Run the Actor and wait for it to finish
run = client.actor("scrapingmonkey/youtube-video-comments-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 '{
  "inputList": [
    "https://www.youtube.com/watch?v=jNQXAC9IVRw"
  ]
}' |
apify call scrapingmonkey/youtube-video-comments-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,scrapingmonkey/youtube-video-comments-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/hq3COHpdizmhthSdr/builds/yk5z6H5u4KdNGDgJ7/openapi.json
