# YouTube Scraper (`hapyco/youtube-scraper`) Actor

Search YouTube by keyword and collect video metadata, comments, and threaded replies. No YouTube API key required. Export structured results to JSON, CSV, or Excel.

- **URL**: https://apify.com/hapyco/youtube-scraper.md
- **Developed by:** [Hapy Co](https://apify.com/hapyco) (community)
- **Categories:** Social media, Videos
- **Stats:** 2 total users, 1 monthly users, 81.8% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

Pay per usage

This Actor is paid per platform usage. The Actor is free to use, and you only pay for the Apify platform usage, which gets cheaper the higher subscription plan you have.

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

## 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

## YouTube Scraper

Search YouTube by keyword and collect video metadata, comments, and threaded replies. Start with search queries, video URLs, or video IDs. No YouTube Data API key or YouTube login is required.

Use the results for brand monitoring, customer feedback research, competitor research, and content analysis. Search covers multiple channels, including third-party channels.

### Quick start

1. Enter a search query or video URLs.
2. Set video, comment, and reply limits.
3. Keep residential proxies enabled for larger runs.
4. Start the Actor.
5. Open the results or export them as JSON, CSV, or Excel.

Start with a small run:

```json
{
  "searchQueries": ["wireless headphones review"],
  "maxResultsPerSearch": 5,
  "maxVideos": 5,
  "maxComments": 20,
  "maxReplies": 10,
  "maxItems": 200,
  "maxRequests": 300,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": ["RESIDENTIAL"]
  }
}
```

For known videos, replace `searchQueries` with `videoUrls`. Watch URLs, Shorts URLs, `youtu.be` URLs, and 11-character video IDs are supported. English, Arabic, and other Unicode queries are supported. Query language does not filter comment language.

### Results

The default dataset contains two record types:

| Type | Contents |
| --- | --- |
| `video` | ID, URL, title, description, channel details, available dates, duration, engagement, thumbnails, and matching queries. |
| `comment` | ID, text, author details, engagement, source publication text, and video details. Replies also have `isReply: true` and `parentCommentId`. |

Use the Overview, Videos, Comments, and Replies views to select result columns. These views do not filter rows. Use `type` and `isReply` to identify record types. Optional values can be null. Missing dates and counts are not invented. `publishedTimeText` preserves source text such as “2 weeks ago”; it is not an exact timestamp.

The key-value store contains:

- `OUTPUT`: final collection report, limits, request counts, and errors.
- `PROGRESS`: outcomes saved after each video.
- `SEARCH`: queries and discovered video IDs when keyword search is used.
- `STATE`: search, completed videos, and cumulative request limits used when the same run resumes.
- `RAW_*`: website responses saved before parsing.

A stopped run can have partial dataset rows and no final report. Check run status and the report before treating collection as complete.

### Limits and coverage

- Search uses YouTube's video search index. It does not guarantee every spoken keyword mention.
- Transcripts, captions, channel enumeration, and media downloads are not supported.
- Enter up to 25 queries or 1,000 known video URLs per input. Search discovery has no fixed video count ceiling.
- Set a count limit to `0` for no count limit: `maxVideos`, `maxResultsPerSearch`, `maxItems`, `maxComments`, `maxReplies`, and `maxRequests`. Collection stops when results end or the two-hour run limit is reached. Checkpoints are saved before shutdown.
- Top-level comments and replies have separate per-video limits. `maxReplies` is a total per video, not per thread. Disable `includeCommentReplies` to skip replies.
- Set `commentsSortBy` to `newest` or `top`. Collection stops at the configured limits.
- Deleted, private, restricted, or unavailable content may fail to load. YouTube can block requests or change its website.
- Larger direct runs can encounter IP blocks. Residential proxies are recommended.
- Resurrect the same interrupted run to resume from its checkpoints. Completed videos are skipped, saved dataset rows are deduplicated, and the request and item limits still apply. A new run starts a new collection.
- To split a large collection, set `maxVideosPerBatch`. A paused segment has `resumeAvailable: true` in `OUTPUT` and a failed run status to keep incomplete collection visible. Resurrect it to collect the next segment. The Actor does not automatically start more paid segments.
- Empty comments pages are recorded as unavailable. Individual video errors appear in `OUTPUT` as warnings. Fatal errors, paused segments, and runs where every attempted collection fails retain a failed status.
- Use 1 GB for larger runs. The default timeout is two hours. More memory does not increase this collector's concurrency.

### API and scheduling

Use the API tab for authenticated request examples. Run the Actor by name, `hapyco/youtube-scraper`, or its Actor ID. Apify tasks and schedules can repeat the configured input. Keep API credentials in authorization headers.

### Pricing

This Actor has no additional Actor fee, per-result fee, or monthly rental. You pay Apify's standard resource charges, including compute, proxies, storage, and data transfer. Residential proxy traffic can be the main cost. The Pricing tab is the source of truth for current charges. Start with a small collection and limit videos, comments, replies, and requests to control usage.

### Support

Use the Issues tab. Include the run ID, expected result, and observed result. Remove credentials and private information before sharing examples.

# Actor input Schema

## `videoUrls` (type: `array`):

Enter up to 1000 known videos, or use search queries.

## `searchQueries` (type: `array`):

Enter up to 25 queries. Results are videos, not channels or playlists.

## `maxResultsPerSearch` (type: `integer`):

Maximum video results per query. Set 0 for all available results within the run time limit.

## `maxVideos` (type: `integer`):

Maximum unique videos across all queries and supplied URLs. Set 0 for no count limit.

## `maxVideosPerBatch` (type: `integer`):

Optional limit on newly processed videos per segment. Resurrect the same run to continue. Set 0 or omit to use the total video limit.

## `maxItems` (type: `integer`):

Maximum dataset rows, including video metadata, comments, and replies. Set 0 for no count limit.

## `scrapeVideoMetadata` (type: `boolean`):

Collect title, description, channel, dates, and engagement.

## `scrapeComments` (type: `boolean`):

Collect comments on discovered and supplied videos.

## `includeCommentReplies` (type: `boolean`):

Collect replies with parent comment IDs.

## `commentsSortBy` (type: `string`):

Choose newest first or top comments.

## `maxComments` (type: `integer`):

Maximum top-level comments per video. Set 0 for all available comments.

## `maxReplies` (type: `integer`):

Maximum replies per video. Set 0 for all available replies. Disable Replies to skip them.

## `maxRequests` (type: `integer`):

Maximum YouTube HTTP requests, including retries. Set 0 for no count limit. The run time limit still applies.

## `proxyConfiguration` (type: `object`):

Use residential proxies for full collections. Small direct tests can work, but large direct runs hit YouTube IP limits.

## Actor input object example

```json
{
  "videoUrls": [
    "https://www.youtube.com/watch?v=YWCKvVNHHP8"
  ],
  "maxResultsPerSearch": 50,
  "maxVideos": 1,
  "maxItems": 20,
  "scrapeVideoMetadata": true,
  "scrapeComments": true,
  "includeCommentReplies": true,
  "commentsSortBy": "newest",
  "maxComments": 5,
  "maxReplies": 5,
  "maxRequests": 50,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ]
  }
}
```

# Actor output Schema

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

Dataset rows use type=video or type=comment. Replies use isReply=true and parentCommentId. Transcripts are not collected.

## `report` (type: `string`):

Final limits, request counts, video outcomes, and errors. This record can be absent if the run is stopped before completion.

## `progress` (type: `string`):

Outcomes saved after each processed video. Empty or missing until the first video finishes.

## `search` (type: `string`):

Search queries, pagination, and discovered video IDs. Present when keyword search is used.

# 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 = {
    "videoUrls": [
        "https://www.youtube.com/watch?v=YWCKvVNHHP8"
    ],
    "maxVideos": 1,
    "maxItems": 20,
    "maxComments": 5,
    "maxReplies": 5,
    "maxRequests": 50
};

// Run the Actor and wait for it to finish
const run = await client.actor("hapyco/youtube-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 = {
    "videoUrls": ["https://www.youtube.com/watch?v=YWCKvVNHHP8"],
    "maxVideos": 1,
    "maxItems": 20,
    "maxComments": 5,
    "maxReplies": 5,
    "maxRequests": 50,
}

# Run the Actor and wait for it to finish
run = client.actor("hapyco/youtube-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 '{
  "videoUrls": [
    "https://www.youtube.com/watch?v=YWCKvVNHHP8"
  ],
  "maxVideos": 1,
  "maxItems": 20,
  "maxComments": 5,
  "maxReplies": 5,
  "maxRequests": 50
}' |
apify call hapyco/youtube-scraper --silent --output-dataset

```

## MCP server setup

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