# Reddit Comment & Top Ranking Scraper (`api-empire/reddit-comment-scraper`) Actor

Reddit Comment & Top Ranking Scraper: Extract Reddit comments, scores, authors, timestamps, replies, and post rankings. Analyze top-performing discussions, audience sentiment, engagement trends, and popular content for Reddit research, competitor analysis, and content strategy.

- **URL**: https://apify.com/api-empire/reddit-comment-scraper.md
- **Developed by:** [API Empire](https://apify.com/api-empire) (community)
- **Categories:** Social media, Automation, Lead generation
- **Stats:** 2 total users, 0 monthly users, 69.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $4.99 / 1,000 results

This Actor is paid per event and usage. You are charged both the fixed price for specific events and for Apify platform usage.

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

### Reddit Comment Scraper — Extract Comments, Rankings & Karma

Reddit Comment & Top Ranking Scraper extracts comments from one or more Reddit posts — or discovers posts by subreddit, search URL, or keyword — and returns them as ranked, typed JSON. Each row carries the comment text, exact upvote count, a locally computed `rank_in_post`, a `controversy_score`, direct-reply counts, and optional author karma/account-age data. Point it at a thread (or a whole subreddit) and get a clean dataset you can sort, merge across posts into a single leaderboard, or feed straight into an LLM pipeline.

### What is Reddit Comment & Top Ranking Scraper?

Reddit Comment & Top Ranking Scraper is an Apify Actor that fetches comments from public Reddit threads, normalizes them into flat JSON rows, and ranks them by real upvote count. It can also discover posts on its own (by subreddit, search URL, or keyword), merge the top comments from multiple posts into one cross-post leaderboard, and optionally enrich each commenter with karma and account-age data. No Reddit account, app registration, or OAuth token is required — it only reads publicly accessible pages.

- Scrape ranked comments (including nested replies) from any public Reddit post
- Discover posts automatically from subreddit URLs, search URLs, or a plain keyword
- Merge top comments from multiple posts into a single cross-post leaderboard
- Enrich commenters with karma totals, account age, and trophy list
- Export results as JSON, CSV, or Excel directly from the Actor's dataset

### How this Actor reads Reddit (and why it matters)

Reddit exposes several different data surfaces, and they do **not** all still work:

| Surface | Status (2026) | Used here |
| --- | --- | --- |
| Legacy public JSON API (`<url>.json`), cookie-less | **Blocked** — returns HTTP 403 for unauthenticated clients on every IP type | No |
| Legacy public JSON API (`<url>.json`), with a warmed anonymous session cookie | **Working** — verified live | **Yes** |
| Official OAuth Data API | Requires app registration, credentials and paid quota tiers | No |
| `old.reddit.com` server-rendered HTML | **Fully login-walled** — every path now 302-redirects to a login page, even the homepage | No |
| `www.reddit.com`'s Shreddit frontend | JS-rendered web components, not server-rendered markup — not scraped | No |

The Actor reads `www.reddit.com`'s JSON API directly (subreddit/search/user listings, a post's comment tree, `/api/morechildren`, and a user's `about.json`), the same one a browser's own page uses internally — not `old.reddit.com`'s HTML, which Reddit has since fully gated behind login. Two details are load-bearing and handled automatically:

- A cookie-less request to any `.json` endpoint gets HTTP 403. Before the first real request, the Actor visits `https://www.reddit.com/` in the same session and, if Reddit serves a lightweight JS-challenge page instead of the real homepage, solves it (no JS runtime needed — the challenge is a plaintext seed-doubling function) to obtain a real anonymous session cookie. No Reddit login or account is used or required.
- NSFW subreddits require the `over18` cookie, which the Actor sets by default (use `safeSearch` to exclude NSFW results from discovery).

If a connection is refused the Actor automatically walks a ladder — your own proxy choice, then a direct connection, then Apify residential / datacenter / static-US proxies — rotating exit IP and TLS fingerprint, warming a fresh anonymous session on each tier, and pins whatever combination first returns a real JSON payload for the rest of the run. Responses that return HTTP 200 but are actually a block/challenge page (never valid JSON) are detected and rejected rather than parsed as empty results.

### What data does Reddit Comment & Top Ranking Scraper collect?

| Data Type | Key Fields | JSON Field Names |
| --- | --- | --- |
| Ranked comments | comment text, exact upvotes, local rank, controversy score, direct replies, timestamps | `contentText`, `upvotes`, `rank_in_post`, `controversy_score`, `reply_count`, `created_time` |
| Nested replies | reply tree embedded per comment, depth-limited | `replies[]` |
| Cross-post leaderboard | comments merged across all submitted/discovered posts, ranked by upvotes | `topCommentsAcrossPosts`, `rank_overall` |
| Author profile data | karma totals, account creation date, trophies, Reddit Premium status | `authorProfile.totalKarma`, `authorProfile.accountCreatedUtc`, `authorProfile.trophies`, `authorProfile.isGold` |
| Post discovery metadata | how a post was found and its real title | `discovered_via`, `discovered_post_title`, `post_id` |

### How does this differ from the official Reddit API?

Reddit's official Data API requires registering an app on Reddit, authenticating with OAuth, and working within Reddit-enforced rate limits — access terms that changed significantly in 2023 when Reddit introduced paid pricing tiers. Reddit Comment & Top Ranking Scraper reads publicly accessible comment pages without any app registration or OAuth token, and adds ranking logic Reddit's API doesn't compute for you.

| Feature | Official Reddit API | Reddit Comment & Top Ranking Scraper |
| --- | --- | --- |
| Authentication | Reddit app registration + OAuth token | None — reads public pages directly |
| Setup process | Register app, request scopes, manage tokens | Paste a URL or keyword, run |
| Ranking | Returns Reddit's own listing order only | Computes `rank_in_post` and `controversy_score` locally |
| Multi-post aggregation | Not provided — one thread per call | Optional cross-post leaderboard across all posts |
| Output format | Raw nested Reddit JSON you must parse yourself | Flat, normalized JSON rows with stable field names |

### Why do developers and teams scrape Reddit?

#### For AI engineers and agent builders

Reddit threads are a dense source of real human opinion, which makes ranked comments useful as RAG context or fine-tuning data. Because `rank_in_post` and `controversy_score` are computed after all reply batches are merged, you can index only the top N comments per post into a vector store instead of the full unranked thread. The flat JSON output — no HTML, no nested listing structures to unwind — drops straight into an embedding pipeline or an agent's tool-call response.

#### For marketers and brand teams

Brand and product teams use Reddit to track what real users say outside curated review sites. Running `searchQuery` or subreddit `searchUrls` with `sinceDate`/`untilDate` lets a team pull comments mentioning a product or competitor from a specific window, then sort by `upvotes` or `controversy_score` to surface reactions that actually gained traction. Enabling `enableCrossPostRanking` turns scattered mentions across several threads into one ranked view.

#### For researchers and analysts

Researchers use Reddit's public comment history to study community sentiment, discourse patterns, or how discussions evolve. The optional `enrichAuthorProfile` field adds `totalKarma`, `commentKarma`, and `accountCreatedUtc` per commenter, letting a researcher correlate account age or karma with participation patterns.

#### For developers building data products

Teams building trend dashboards can schedule this Actor against a fixed list of subreddits or keywords and use the `topCommentsAcrossPosts` leaderboard as a ready-made "what's rising across these threads right now" feed. Output field names don't change between runs.

### How to scrape Reddit (step by step)

1. Open Reddit Comment & Top Ranking Scraper on its Apify Store page and click **Run**.
2. Provide input: paste one or more URLs into `redditPostUrls`, or leave it empty and use `searchUrls` / `searchQuery` to have the Actor discover posts for you.
3. Set `sortMode`, `maxCommentsPerPost`, `maxReplyDepth`, and optionally `sinceDate`/`untilDate`.
4. Start the run — comments are fetched, deduplicated, capped, and ranked.
5. Download results as JSON, CSV, or Excel from the run's dataset, or read `topCommentsAcrossPosts` from the key-value store if cross-post ranking was enabled.

### ⬇️ Input

| Parameter | Required | Type | Description | Example Value |
| --- | --- | --- | --- | --- |
| `redditPostUrls` | No | array | Reddit post URLs to fetch and rank comments from. Also accepts `startUrls`. | `["https://www.reddit.com/r/AskReddit/comments/1vdjhvv/"]` |
| `maxCommentsPerPost` | No | integer | Hard cap on comments returned per post (1–10,000). Selection respects `sortMode` (see below). Also accepts `maxComments`. | `100` |
| `maxReplyDepth` | No | integer | How many **levels** of nested replies to embed in each comment's `replies` array (1 = direct replies only, 0 = unlimited). Does not limit how many comments are scraped. Also accepts `replyLimit`. | `2` |
| `sortMode` | No | string (enum) | Which comments Reddit serves, and how the cap selects them. One of `hot`, `new`, `top`, `controversial`, `old`. Also accepts `sortOrder`. | `top` |
| `searchUrls` | No | array | Subreddit listing, subreddit search, site search, or user URLs to discover posts from. | `["https://www.reddit.com/r/ChatGPT/top/?t=week"]` |
| `searchQuery` | No | string | Plain keyword/phrase to search Reddit site-wide for matching posts. | `"gpt5 launch"` |
| `maxPostsToDiscover` | No | integer | Max posts discovered in total across `searchUrls` and `searchQuery` (1–500). Ignored when only direct URLs are used. | `10` |
| `safeSearch` | No | boolean | Skip NSFW (`over_18`) posts found via discovery. No effect on direct `redditPostUrls`. | `false` |
| `sinceDate` | No | string | Only keep comments created on/after this date. Absolute date or relative like `3 days` / `1 week`. | `"1 week"` |
| `untilDate` | No | string | Only keep comments created on/before this date. Same format as `sinceDate`. | `"2026-01-01"` |
| `enrichAuthorProfile` | No | boolean | Add an `authorProfile` object (karma, account age, trophies, Premium) per row, resolved once per unique author (max 300 per run). | `false` |
| `enableCrossPostRanking` | No | boolean | Merge comments from every post by upvotes into one leaderboard (`topCommentsAcrossPosts`). | `false` |
| `crossPostLeaderboardSize` | No | integer | Max comments kept in the merged leaderboard (1–500). Ignored unless cross-post ranking is on. | `50` |
| `proxyConfiguration` | No | object | Proxy settings. Your selection is tried first; the Actor falls back through direct, residential, datacenter and static-US proxies automatically. | `{"useApifyProxy": false}` |

No input parameter is required, but the Actor needs at least one of `redditPostUrls`, `searchUrls`, or `searchQuery` to know what to fetch. If it can't extract a single comment from any target, the run **fails** with an explicit status message rather than reporting a misleading success.

#### How `sortMode` and `maxCommentsPerPost` interact

`sortMode` changes **which** comments Reddit hands over, not just their order — Reddit only serves a slice of a large thread per sort. `maxCommentsPerPost` is then applied as a hard cap using the metric that sort mode implies:

| `sortMode` | Cap keeps | Typical use |
| --- | --- | --- |
| `top` | The N highest-scoring comments in the thread | "Top comments" leaderboards |
| `new` | The N newest comments | Live monitoring (scores are usually still hidden by Reddit) |
| `old` | The N oldest comments | Reaching the beginning of a thread; pairs well with `untilDate` |
| `hot` | The first N in Reddit's own "best" order, top-level first | Mirroring what a visitor sees |
| `controversial` | The first N in Reddit's controversial order, top-level first | Finding contested replies |

`rank_in_post` is always recomputed from real upvote counts (descending) over whatever set was kept.

Example JSON input:

```json
{
  "redditPostUrls": ["https://www.reddit.com/r/AskReddit/comments/1vdjhvv/"],
  "maxCommentsPerPost": 200,
  "maxReplyDepth": 2,
  "sortMode": "top",
  "searchUrls": ["https://www.reddit.com/r/ChatGPT/top/?t=week"],
  "searchQuery": "gpt5 launch",
  "maxPostsToDiscover": 20,
  "safeSearch": true,
  "sinceDate": "1 week",
  "untilDate": "",
  "enrichAuthorProfile": true,
  "enableCrossPostRanking": true,
  "crossPostLeaderboardSize": 50,
  "proxyConfiguration": { "useApifyProxy": false }
}
```

### ⬆️ Output

Every run pushes typed, normalized JSON rows to the Actor's dataset, exportable as JSON, CSV, or Excel. `authorProfile` only appears when `enrichAuthorProfile` is enabled, and the cross-post leaderboard dataset only exists when `enableCrossPostRanking` is enabled.

#### Scraped comments

```json
{
  "url": "https://www.reddit.com/r/AskReddit/comments/1vdjhvv/",
  "comment_id": "p19enka",
  "post_id": "t3_1vdjhvv",
  "author": "jmills23",
  "permalink": "https://www.reddit.com/r/AskReddit/comments/1vdjhvv/for_women_who_never_wear_makeup_what_lead_you_to/p19enka/",
  "upvotes": 26938,
  "score_hidden": false,
  "reply_count": 27,
  "content_type": "comment",
  "parent_id": "1vdjhvv",
  "author_avatar": "",
  "userUrl": "https://www.reddit.com/user/jmills23/",
  "contentText": "Laziness, prioritizing sleep over it, the cost, I never had the patience to learn how to do it well...",
  "created_time": "2026-08-02T14:33:52Z",
  "replies": [
    {
      "comment_id": "p19flah",
      "author": "Flimsy_Fee8449",
      "upvotes": 4748,
      "contentText": "Oh, good morning, are you me? Yep, I would rather sleep in...",
      "created_time": "2026-08-02T14:38:29Z",
      "permalink": "https://www.reddit.com/r/AskReddit/comments/1vdjhvv/.../p19flah/",
      "userUrl": "https://www.reddit.com/user/Flimsy_Fee8449/",
      "replies": []
    }
  ],
  "rank_in_post": 1,
  "controversy_score": 960.0,
  "is_top_level": true,
  "discovered_via": "direct_url",
  "discovered_post_title": "For women who NEVER wear makeup, what lead you to that choice?"
}
```

Field notes:

- `upvotes` is Reddit's exact score straight from its JSON API — not the rounded "26.9k" display value.
- `score_hidden` is `true` for very new comments where Reddit deliberately hides the score; `upvotes` is then `0`.
- `content_type` is one of `comment`, `reply`, `link`, `deleted`, `removed`, `empty`.
- `media_urls` holds any image/GIF/link URLs found in the comment body. Image-only comments have an empty `contentText` but a populated `media_urls` and `content_type: "link"`.
- `controversy_score` is a custom metric: `upvotes / (direct replies + 1)`.
- `author_avatar` is usually an empty string — Reddit's avatar image isn't part of the comment payload. It is populated only when `enrichAuthorProfile` finds one on the author's public profile.

#### Cross-post leaderboard (`topCommentsAcrossPosts`)

Only produced when `enableCrossPostRanking` is `true`. Same row shape as above, saved to a named dataset (`top-comments-across-posts`) and to the key-value store, plus one added field:

```json
{
  "url": "https://www.reddit.com/r/AskReddit/comments/1vdjhvv/",
  "comment_id": "p19enka",
  "author": "jmills23",
  "upvotes": 26959,
  "rank_in_post": 1,
  "rank_overall": 1
}
```

#### Author profile enrichment (`authorProfile`)

Present per comment only when `enrichAuthorProfile` is `true`, resolved once per unique author:

```json
{
  "totalKarma": 29950,
  "postKarma": 2857,
  "commentKarma": 27093,
  "accountCreatedUtc": "2015-04-05T13:49:07Z",
  "isGold": false,
  "trophies": ["11-Year Club", "RedditGifts 2009-2022", "Verified Email"]
}
```

`isGold` is Reddit's own field from the author's public profile data. `trophies` is currently always an empty list — the trophy list lives on a separate endpoint that isn't fetched, to keep author enrichment at one request per unique author.

### How many results can you scrape?

`maxCommentsPerPost` caps the Actor at 1–10,000 comments per post; there is no schema cap on how many post URLs you can submit. Reddit itself limits how much of a thread it will serve for a given sort — a single sort typically reaches several hundred to a few thousand comments of a very large thread, and deep branches are expanded through `morechildren` automatically. To reach different regions of a huge thread, run it more than once with different `sortMode` values (for example `top` and `old` + `untilDate`).

When discovering posts, `maxPostsToDiscover` caps discovery at 1–500 posts combined across all `searchUrls` and `searchQuery`. `enrichAuthorProfile` resolves up to 300 unique authors per run. The cross-post leaderboard keeps 1–500 comments.

### Integrate Reddit Comment & Top Ranking Scraper and automate your workflow

#### REST API integration

```python
import requests

TOKEN = "YOUR_APIFY_API_TOKEN"
ACTOR = "your-username~reddit-comment-top-ranking-scraper"

resp = requests.post(
    f"https://api.apify.com/v2/acts/%7BACTOR%7D/run-sync-get-dataset-items",
    params={"token": TOKEN},
    json={"redditPostUrls": ["https://www.reddit.com/r/AskReddit/comments/1vdjhvv/"],
          "sortMode": "top", "maxCommentsPerPost": 50},
)
resp.raise_for_status()
comments = resp.json()
print(comments[0]["contentText"], comments[0]["rank_in_post"])
```

Works in Python, Node.js, Go, Ruby, cURL.

#### MCP for AI agents

Any Apify Actor, including this one, can be exposed to an MCP-compatible client through Apify's hosted Actors MCP Server, e.g. `npx -y @apify/actors-mcp-server --actors your-username/reddit-comment-top-ranking-scraper`.

#### Automation platforms (n8n, Make)

In n8n, the community "Apify" node can call this Actor by its Actor ID and pass through the same input JSON. In Make, the "Apify" app's "Run Actor" module accepts this Actor's ID and input.

### Is it legal to scrape Reddit?

This Actor only reads comments and post data that are already publicly visible on reddit.com, without logging in or accessing anything behind a private subreddit or login wall. Reddit usernames are pseudonymous handles, but commenter data — especially combined with karma and account-age fields from `enrichAuthorProfile` — can still be considered personal data under regulations like GDPR or CCPA. Storing or reusing bulk commenter data at scale should have a documented lawful basis. Consult legal counsel for commercial use cases involving bulk personal data.

### Frequently asked questions

#### Does it work without a Reddit account?

Yes. The Actor establishes an anonymous session the same way a logged-out browser tab does (solving a lightweight JS challenge if Reddit serves one) and reads Reddit's own public JSON API with it — no Reddit login, app registration, or OAuth token is needed.

#### Reddit's `.json` endpoints stopped working for me. Does that affect this Actor?

Reddit does return HTTP 403 for a cookie-less request to those endpoints. This Actor works around that by obtaining a real anonymous session cookie first (see "How this Actor reads Reddit" above), then using the same `.json` endpoints with that cookie — which Reddit serves normally. `old.reddit.com`'s HTML, which a prior version of this Actor used, is no longer usable at all: Reddit now redirects every path on that subdomain to a login wall, logged-in or not.

#### How often is the scraped data updated?

Every run fetches comments live from Reddit at the time it executes; nothing is cached. Running the Actor again returns the current state of the thread, including new comments and updated upvote counts.

#### What happens if a post has no comments or was deleted?

Other URLs in the same batch are unaffected. Comments authored by deleted accounts or removed by moderators are still returned, tagged `content_type: "deleted"` or `"removed"` — and, importantly, their surviving child replies are still scraped. If *no* target yields a single comment, the run fails with an explicit message.

#### Can I scrape private or quarantined subreddit content?

No. The Actor only reaches subreddits and posts that are publicly accessible without logging in.

#### How does "top ranking" actually work?

Two things combine. First, `sortMode: "top"` asks Reddit for its genuine top-sorted comment listing, so the comments you receive are the ones Reddit itself ranks highest. Second, `rank_in_post` is recomputed locally from each comment's exact upvote count after every reply batch has been merged, so the numbering is consistent even across `morechildren` pages. `controversy_score` is a custom metric (`upvotes / (direct replies + 1)`), not something Reddit exposes.

#### Why are `upvotes` 0 on many comments when I use `sortMode: "new"`?

Reddit deliberately hides scores on very recent comments. Those rows carry `score_hidden: true`. Use `sortMode: "top"` if you need scored comments.

#### How does the Actor handle Reddit's anti-bot defenses?

Before its first real request, the Actor establishes a real anonymous session cookie with Reddit (solving a lightweight JS challenge if one is served) — the same cookie a logged-out browser tab would get. Requests use a Firefox/Safari-matching TLS fingerprint via `curl_cffi`, and the Actor rotates exit IP and fingerprint across a proxy ladder (warming a fresh session on each tier) until it gets a genuine JSON response, then pins that combination. Responses that return HTTP 200 but aren't valid JSON (a block or challenge page) are detected and rejected instead of being parsed as empty results.

### Your feedback

Found a bug, a missing field, or a case where ranking looks off? Reach out through the Actor's Issues tab on its Apify Store page.

# Actor input Schema

## `redditPostUrls` (type: `array`):

📋 Paste one or more Reddit post URLs. Each post's comments are fetched, ranked by upvotes, and (optionally) merged into a cross-post leaderboard.

Example: https://www.reddit.com/r/subreddit/comments/post\_id/title/

Also accepts the base field name `startUrls` for backward compatibility.

## `maxCommentsPerPost` (type: `integer`):

⚙️ Maximum number of comments to extract and rank per post. Range: 1-10,000. Also accepts the base field name `maxComments`.

## `maxReplyDepth` (type: `integer`):

🌳 How many LEVELS of nested replies to embed inside each comment's `replies` field (1 = direct replies only, 2 = replies + their replies, 0 = unlimited depth). This only shapes the nested `replies` field — every reply is still scraped, ranked and returned as its own flat row regardless of this value. Use 🔢 Maximum Comments per Post to cap volume. Also accepts the legacy field name `replyLimit`.

## `sortMode` (type: `string`):

🔽 The comment order Reddit itself serves — this genuinely changes WHICH comments you get, not just their order, because Reddit only returns a slice of a large thread. Use ⬆️ Top for real top-ranked comments, 🆕 New for the latest ones, 🕰️ Old together with 📅 Only Comments Until to reach older parts of a thread. `rank_in_post` is always recomputed from real upvotes. Also accepts the legacy field name `sortOrder`.

## `searchUrls` (type: `array`):

🕵️ Paste subreddit listing URLs (e.g. https://www.reddit.com/r/ChatGPT/) or Reddit search URLs (e.g. https://www.reddit.com/r/ChatGPT/search/?q=gpt5) to discover posts to rank, instead of pasting individual post URLs.

## `searchQuery` (type: `string`):

💡 A plain keyword/phrase to search Reddit site-wide for matching posts (used together with or instead of 🌐 Subreddit / Search URLs).

## `maxPostsToDiscover` (type: `integer`):

📈 Maximum number of posts to discover in total from 🌐 Subreddit / Search URLs and 🔑 Keyword Search Query combined. Ignored when only direct 🔗 Reddit Post URLs are used.

## `safeSearch` (type: `boolean`):

🔞 When enabled, skip over\_18/NSFW posts found via discovery. Has no effect on directly-provided 🔗 Reddit Post URLs.

## `sinceDate` (type: `string`):

⏱️ Only rank comments created on/after this date. Accepts an absolute date or a relative value like `3 days`/`1 week`.

## `untilDate` (type: `string`):

⏱️ Only rank comments created on/before this date. Accepts an absolute date or a relative value like `3 days`/`1 week`.

## `enrichAuthorProfile` (type: `boolean`):

📈 When enabled, adds an `authorProfile` object (post/comment/total karma, account creation date, trophy list, Reddit Premium status) to every comment row, resolved once per unique author (max 300 unique authors per run).

## `enableCrossPostRanking` (type: `boolean`):

📊 When enabled, the top comments from every submitted post are merged by upvotes into a single cross-post leaderboard (`topCommentsAcrossPosts`), saved as a named dataset and to the key-value store. When disabled, only the per-post ranked rows are produced (matches base behavior).

## `crossPostLeaderboardSize` (type: `integer`):

🔝 Maximum number of top-ranked comments to keep in the merged cross-post leaderboard when 'Merge Comments Across All Posts' is enabled. Ignored otherwise.

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

🔒 Configure proxy settings. Your selection here is tried first (after a direct attempt); if it fails, the scraper automatically falls back through datacenter then residential proxies with retries. By default, no proxy is used.

## Actor input object example

```json
{
  "redditPostUrls": [
    "https://www.reddit.com/r/ChatGPT/comments/1epeshq/these_are_all_ai/"
  ],
  "maxCommentsPerPost": 100,
  "maxReplyDepth": 2,
  "sortMode": "hot",
  "searchUrls": [],
  "maxPostsToDiscover": 10,
  "safeSearch": false,
  "enrichAuthorProfile": false,
  "enableCrossPostRanking": false,
  "crossPostLeaderboardSize": 50,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}
```

# Actor output Schema

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

All ranked comments from every post, one row per comment (default dataset).

## `topCommentsAcrossPosts` (type: `string`):

The merged top-ranked comments across all posts by upvotes. Only populated when 'Merge Comments Across All Posts into One Leaderboard' is enabled.

## `commentsByUrl` (type: `string`):

A single JSON record grouping all ranked comments by their source post URL.

## `topCommentsAcrossPostsRecord` (type: `string`):

The same cross-post leaderboard as a single key-value store record. Only populated when 'Merge Comments Across All Posts into One Leaderboard' is enabled.

# 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 = {
    "redditPostUrls": [
        "https://www.reddit.com/r/ChatGPT/comments/1epeshq/these_are_all_ai/"
    ],
    "maxCommentsPerPost": 100,
    "maxReplyDepth": 2,
    "sortMode": "hot",
    "searchUrls": [],
    "searchQuery": "",
    "proxyConfiguration": {
        "useApifyProxy": false
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("api-empire/reddit-comment-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 = {
    "redditPostUrls": ["https://www.reddit.com/r/ChatGPT/comments/1epeshq/these_are_all_ai/"],
    "maxCommentsPerPost": 100,
    "maxReplyDepth": 2,
    "sortMode": "hot",
    "searchUrls": [],
    "searchQuery": "",
    "proxyConfiguration": { "useApifyProxy": False },
}

# Run the Actor and wait for it to finish
run = client.actor("api-empire/reddit-comment-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 '{
  "redditPostUrls": [
    "https://www.reddit.com/r/ChatGPT/comments/1epeshq/these_are_all_ai/"
  ],
  "maxCommentsPerPost": 100,
  "maxReplyDepth": 2,
  "sortMode": "hot",
  "searchUrls": [],
  "searchQuery": "",
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}' |
apify call api-empire/reddit-comment-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,api-empire/reddit-comment-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/Z0oZYqEyGtNGl9rc1/builds/kZ1CnQaGJysBxui6h/openapi.json
