YouTube Comments Scraper avatar

YouTube Comments Scraper

Pricing

from $0.50 / 1,000 comment scrapeds

Go to Apify Store
YouTube Comments Scraper

YouTube Comments Scraper

Export every comment and reply from any public YouTube video into clean, structured dataset rows — author, text, like count, reply count, pinned/hearted flags, sorted by top or newest. Devil Scrapes tracks YouTube's shifting internal API so your pipeline doesn't break. Bulk export to JSON or CSV.

Pricing

from $0.50 / 1,000 comment scrapeds

Rating

0.0

(0)

Developer

DevilScrapes

DevilScrapes

Maintained by Community

Actor stats

0

Bookmarked

2

Total users

1

Monthly active users

21 days ago

Last modified

Share


🎯 What this scrapes

YouTube's own video page walks a two-step internal API to load comments: fetch the watch payload, pull a continuation token out of its comments-section engagement panel, then page through /youtubei/v1/next for the actual comment nodes. We do the same walk — a generic recursive search finds that token wherever YouTube's payload nests it this month, so a client-side layout shift doesn't quietly break the scrape — and turn every comment and reply into one clean dataset row, sorted by top or newest comments, with optional full reply threads.

🔥 What we handle for you

  • 🛡️ Browser fingerprint rotation — curl-cffi impersonates real Chrome / Firefox / Safari TLS handshakes so the target sees a browser, not Python.
  • 🌐 Residential proxy rotation via Apify Proxy — fresh session and exit IP on every block.
  • 🔁 Retries with exponential backoff on 408 / 429 / 5xx — up to 5 attempts per page, Retry-After honoured.
  • 🧱 Rate-limit-aware pacing — when the target pushes back, we slow down instead of getting banned.
  • 🧊 Clean, typed dataset rows — Pydantic-validated, ISO-8601 timestamps, stable IDs, JSON / CSV / Excel export straight from the Apify Console.
  • 💰 Pay-Per-Event pricing — you only pay for results that hit your dataset. No data, no charge.

💡 Use cases

  • Social listening — pull every comment on a video the moment it lands and feed sentiment/topic models in near real time.
  • Brand monitoring — track what viewers say under a brand's own uploads or under mentions in a competitor's videos.
  • Creator analytics — give creators and their teams a clean export of audience reaction, sorted top or newest, without babysitting the YouTube UI.
  • NLP pipelines — bulk comment/reply text with stable IDs for training or evaluating classifiers, topic models, and toxicity filters.

⚙️ How to use it

  1. Click Try for free at the top of the page.
  2. Fill in the input form — most fields have sensible defaults.
  3. Click Start. Output streams into the run's dataset.
  4. Export from Storage → Dataset as JSON, CSV, or Excel — or fetch via the API.

📥 Input

FieldTypeRequiredDefaultNotes
videoUrlsarrayyes['https://www.youtube.com/watch?v=dQw4w9WgXcQ']YouTube video URLs, short URLs (youtu.be/...), Shorts URLs, or bare 11-character video IDs. Mix and match…
maxCommentsintegerno100Stop paging once this many top-level comments (and replies, if included) have been emitted for a single video…
sortBystringno'top'Comment order YouTube returns — matches the sort control on the video page itself.
includeRepliesbooleannoFalseFollow each top-level comment's reply thread too. Multiplies request volume and cost — leave off unless you need full…
hlstringno'en'YouTube UI language passthrough — affects relative-timestamp text like "1 year ago". Example: en.
glstringno'US'YouTube UI country/region passthrough. Example: US.
proxyConfigurationobjectno{'useApifyProxy': True}Apify Proxy configuration. Recon confirmed byte-identical comment payloads across datacenter and residential exits —…

Example input

{
"videoUrls": [
"https://www.youtube.com/watch?v=dQw4w9WgXcQ",
"https://www.youtube.com/watch?v=jNQXAC9IVRw"
],
"maxComments": 45,
"sortBy": "top",
"includeReplies": false,
"hl": "en",
"gl": "US",
"proxyConfiguration": {
"useApifyProxy": false
}
}

📤 Output

Every row is one dataset item.

FieldTypeNotes
video_idstring11-character YouTube video ID this comment belongs to.
comment_idstringYouTube's opaque comment/reply ID.
authorstringCommenter's display name at scrape time.
author_channel_idstringCommenter's channel ID. Null when YouTube omits it (e.g. deleted account).
textstringComment or reply body, plain text.
published_timestringYouTube's relative publish string (e.g. '1 year ago'), verbatim — YouTube does not expose an absolute timestamp on this…
like_countintegerLike count at scrape time. Defaults to 0 when absent.
reply_countintegerNumber of replies under this top-level comment. 0 for replies themselves.
is_pinnedbooleanTrue when the video owner pinned this comment.
is_heartedbooleanTrue when the video owner hearted this comment.
is_replybooleanTrue for a reply row, false for a top-level comment.
parent_comment_idstringThe top-level comment_id this row replies to. Null for top-level comments.

Example output

{
"video_id": "dQw4w9WgXcQ",
"comment_id": "Ugzge340dBgB75hWBm54AaABAg",
"author": "SomeUser",
"author_channel_id": "UCxxxxxxxxxxxxxxxxxxxxxx",
"text": "can confirm: he never gave us up",
"published_time": "1 year ago",
"like_count": 1204,
"reply_count": 3,
"is_pinned": false,
"is_hearted": false,
"is_reply": false,
"parent_comment_id": null
}

💰 Pricing

Pay-Per-Event — you pay only when these events fire:

EventUSDWhat it is
actor-start$0.2One-off warm-up charge per run
comment-scraped$0.0005PPE event

Example: 1 000 results at the rates above ≈ $0.70. No subscription, no minimum, no card to start — Apify gives every new account $5 of free credit.

🚧 Limitations

Public comments only — no OAuth, no moderator tools, no comment-author metadata beyond what YouTube's own comments UI exposes. YouTube's internal payload shape can shift between web-client releases; we walk it with a generic recursive search rather than a fixed path, but a structural change may still need a same-day patch. Enabling replies multiplies request volume per video — factor that into cost expectations for reply-heavy videos.

❓ FAQ

Does this scrape live chat?

No — this is the standard comments section under a video, not live-stream chat. For live chat you want a different endpoint entirely.

Why are replies not included by default?

Following every reply thread multiplies request volume (and cost) per video. Turn on includeReplies when you need full threads; leave it off for a fast top-level-only pull.

Why is published_time a string like '1 year ago' instead of a date?

That's what YouTube's own comments endpoint returns — it does not expose an absolute timestamp here. We pass it through verbatim rather than guessing at a conversion.

Why did one video return zero comments?

Comments can be disabled by the uploader, or the video may have none yet. The run still succeeds — it reports how many videos had no comments in the final status message rather than failing the whole run.

What happens if a video ID is invalid or private?

That single video is skipped and counted as failed in the run summary; every other video in the same run still completes.

💬 Your feedback

Spotted a bug, hit a weird edge case, or need a new field? Open an issue on the Actor's Issues tab on Apify Console — we ship fixes weekly and we read every report.