# Fast Twitter (X) Replies Scraper API (`apidojo/twitter-replies-scraper`) Actor

Extract every reply from any Twitter (X) post by Tweet ID or URL with full author data and engagement metrics (likes, replies, reposts, quotes, views). Optional search mode for broader coverage; export to JSON, CSV & Excel. Ideal for brand monitoring, sentiment analysis & competitor research.

- **URL**: https://apify.com/apidojo/twitter-replies-scraper.md
- **Developed by:** [API Dojo](https://apify.com/apidojo) (community)
- **Categories:** Social media, Lead generation, Other
- **Stats:** 3 total users, 2 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $0.40 / 1,000 dataset items

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/platform/actors/running/actors-in-store#pay-per-event

## What's an Apify Actor?

Actors are a software tools running on the Apify platform, for all kinds of web data extraction and automation use cases.
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.

In JavaScript/TypeScript projects, use official [JavaScript/TypeScript client](https://docs.apify.com/api/client/js.md):

```bash
npm install apify-client
```

In Python projects, use official [Python client library](https://docs.apify.com/api/client/python.md):

```bash
pip install apify-client
```

In shell scripts, use [Apify CLI](https://docs.apify.com/cli/docs.md):

````bash
# MacOS / Linux
curl -fsSL https://apify.com/install-cli.sh | bash
# Windows
irm https://apify.com/install-cli.ps1 | iex
```bash

In AI frameworks, you might use the [Apify MCP server](https://docs.apify.com/platform/integrations/mcp.md).

If your project is in a different language, use 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

## 🏯 **Twitter Replies Scraper – Fast, Reliable & Complete Reply Data Extraction**

Extract **X (Twitter) replies**, **tweet comments**, **reply authors**, and **complete engagement metrics** with structured, ready-to-use JSON output. This **Twitter replies scraper** pulls replies straight from a Tweet ID or Tweet URL, no login, no proxy. The most **affordable Apify Twitter reply scraper**, priced per result so you only pay for the data you actually collect.

⚡ **Input:** Tweet ID or Tweet URL — no search syntax required
💰 **Price:** $0.0004 per dataset item + query fee
✅ **Two collection modes:** default replies flow or search-based `conversation_id` flow
📊 **Data Points:** 30+ fields per reply including full author profile and engagement metrics
🎯 **Free Plan friendly:** Demo Mode included for testing before you commit

Looking for a **reliable Twitter (X) replies scraper** to **extract tweet comments**, monitor **brand mentions**, or build a **sentiment analysis dataset**? Need to **scrape replies to any tweet** including **reply author bios, follower counts, and engagement metrics**? This Apify actor delivers complete conversation-level intelligence in one run.

### 📚 Table of Contents

- [🧭 What does Twitter Replies Scraper do?](#what-does-twitter-replies-scraper-do)
- [🐉 Features and Functionality](#features-and-functionality)
- [Important Note About Usage](#important-note-about-usage)
- [⚡ Performance & Technical Details](#performance-and-technical-details)
- [💰 Pricing](#pricing)
- [🆓 Demo Mode & Free Users](#demo-mode-and-free-users)
- [🍚 Input Parameters](#input-parameters)
- [🍜 Output](#output)
- [Search Flow vs Replies Flow](#search-flow-vs-replies-flow)
- [🍳 Custom Map Function](#custom-map-function)
- [🔧 Troubleshooting & Common Issues](#troubleshooting-and-common-issues)
- [🎯 Who Needs This Twitter Replies Scraper? (Use Cases & Industries)](#who-needs-this-twitter-replies-scraper-use-cases-and-industries)
- [💡 How to Scrape Twitter Replies: Step-by-Step Guide](#how-to-scrape-twitter-replies-step-by-step-guide)
- [❓ Frequently Asked Questions (FAQ)](#frequently-asked-questions-faq)
- [Contact](#contact)

### 🧭 What does Twitter Replies Scraper do?

The API Dojo **Twitter Replies Scraper** is a specialized data extraction actor built to **scrape replies, comments, and conversation threads from any public tweet on X (Twitter)**. Give it a Tweet ID or a Tweet URL and it returns every available reply in a clean, structured dataset — without needing proxies, cookies, or a Twitter developer account.

With **automatic pagination**, a **search-based fallback mode** for deeper conversation coverage, and a **custom map function** for on-the-fly field transformation, this scraper gives you full visibility into how people are responding to any post. Whether you're tracking brand sentiment, researching audience reactions, or building a dataset for social listening, Twitter Replies Scraper makes it easy to collect and reshape exactly the reply data you need.

This actor is ideal for **brand monitoring**, **sentiment analysis**, **audience research**, and **lead generation** — helping marketers, community managers, analysts, and growth teams turn raw reply threads into structured, actionable data.

### 🐉 Features and Functionality

The **Twitter Replies Scraper** gives you **complete, structured access** to reply data on X — covering **reply text**, **author profiles**, **engagement metrics**, and **conversation context**. It's built not just for scraping, but for **conversation-level intelligence** — the foundation for brand monitoring, research, and growth workflows at scale.

#### ⚡ Scrape Twitter reply data from:

- ✅ **Any public Tweet** — Provide a Tweet ID or Tweet URL and pull every available reply.
- ✅ **Reply Author Profiles** — Full profile object per reply: bio, followers, following, verification status, join date.
- ✅ **Engagement Metrics** — Likes, retweets, replies, quotes, views, and bookmarks for every reply.
- ✅ **Conversation Context** — `conversationId`, `inReplyToId`, and `inReplyToUsername` so you can rebuild the thread.
- ✅ **Mentions & Entities** — User mentions, hashtags, and other embedded entities extracted per reply.
- ✅ **Reply Source** — The client used to post the reply (web, Android, iOS, third-party apps).

#### 🧠 Smart Functionalities

| **Capability**         | **What It Does**                                                                           | **Why It Matters**                                                                          |
| ---------------------- | ------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------- |
| Tweet ID or URL Input  | Accept either raw Tweet IDs or full Tweet/X URLs interchangeably.                          | Simplifies input whether you're pulling IDs from an API or copy-pasting links.              |
| Dual Collection Modes  | Default replies endpoint, or `useSearch: true` for a `conversation_id:` search-based flow. | Lets you fall back to a broader collection method when the default flow misses replies.     |
| maxItems Control       | Cap total replies collected per run.                                                       | Keeps costs predictable for both quick tests and full-scale pulls.                          |
| Custom Map Function    | Pass a JS function to reshape, rename, or filter fields in every output row.               | Get exactly the schema your downstream tool or database expects, with zero post-processing. |
| Structured Data Output | JSON / CSV / Excel / XML / RSS ready for dashboards, CRMs, or automation platforms.        | Instant integration with your existing tools.                                               |
| No Proxy Required      | Runs smoothly out of the box without additional proxy configuration.                       | Less setup, more scraping.                                                                  |
| Free Plan Demo Mode    | Run the actor up to 5 times per month on Apify's Free Plan, each run capped at 10 items.   | Test the actor and validate the output format at zero cost.                                 |

#### 🧭 Complete Your Twitter Data Stack

Need comprehensive X (Twitter) intelligence? The **Twitter Replies Scraper** works seamlessly alongside other specialized extraction tools to create a **complete data collection ecosystem**. Each actor targets a unique layer of Twitter — from search and profiles to user accounts and reply threads.

By combining these purpose-built scrapers, you can construct **multi-dimensional datasets** for brand monitoring, competitive research, audience analysis, and social listening. Choose the tools that match your specific use case, or deploy them together for maximum coverage.

| 🏯 [**Tweet Scraper**](https://apify.com/apidojo/tweet-scraper) | 🏯 [**Twitter Scraper Lite**](https://apify.com/apidojo/twitter-scraper-lite)       | 🏯 [**Twitter (X) User Scraper**](https://apify.com/apidojo/twitter-user-scraper) |
| -------------------------------------------------------------- | ---------------------------------------------------------------------------------- | -------------------------------------------------------------------------------- |
| **💬 [Twitter Replies Scraper](#)**                             | **👤 [Twitter Profile Scraper](https://apify.com/apidojo/twitter-profile-scraper)** | **📋 [Twitter List Scraper](https://apify.com/apidojo/twitter-list-scraper)**     |

### Important Note About Usage

This scraper is designed to fetch replies from real, public tweets. To ensure stable performance and fair usage, please follow these rules:

- The **tweet must exist and be public**. Deleted, protected, or invalid Tweet IDs/URLs are not supported.
- The tweet should **have replies**. Scraping tweets with zero replies returns an empty dataset and wastes run time.
- Use **`useSearch: true`** if the default replies flow returns fewer results than expected — the search-based flow can surface additional conversation tweets.

### ⚡ Performance & Technical Details

The API Dojo **Twitter Replies Scraper** is engineered to deliver **fast**, **reliable**, and **consistent** reply extraction at scale. With flexible input options, a search-based fallback mode, and a custom map function, it handles everything from a single-thread pull to large conversation-monitoring jobs.

#### 🚀 Key Technical Highlights

| **⚡ Feature**               | **📊 Specification**                      | **🧾 Description**                                                      |
| --------------------------- | ---------------------------------------- | ---------------------------------------------------------------------- |
| 🚀 **Dual Input Methods**    | Tweet ID or Tweet URL                    | Flexible configuration for streamlined data collection                 |
| 🔁 **Dual Collection Modes** | Default replies flow / search-based flow | Broader coverage when the standard endpoint falls short                |
| 🛡️ **No Proxy Required**     | Stable out-of-the-box                    | Runs reliably without additional proxy setup                           |
| 📦 **Structured Output**     | JSON / CSV / Excel / XML / RSS           | Export-ready format for CRMs, databases, and analytics tools           |
| ⚙️ **Custom Configuration**  | maxItems, customMapFunction              | Fine-tune extraction and reshape output to match specific requirements |
| 🆓 **Free Plan Demo Mode**   | 5 runs / month, 10 items / run capped    | Validate output before committing to a paid plan                       |
| 📊 **Rich Data Fields**      | 30+ fields per reply                     | Full reply text, author profile, engagement, and conversation metadata |

#### 🧭 Infrastructure Reliability

This actor is built for **production-grade reply scraping** with enterprise-level stability. Its dual collection modes and automatic pagination maintain consistent coverage across thousands of runs, ensuring reliable performance even during high-volume monitoring jobs. Perfect for continuous brand tracking, ongoing sentiment analysis, and integration with social listening platforms.

### 💰 Pricing

The Apify **Twitter Replies Scraper** uses a transparent, **pay-per-result** pricing model — you're charged for the dataset items you collect plus a small per-query fee, depending on which collection flow you use.

#### 📊 Pricing Overview

| **💵 Pricing Item** | **🧮 Price** | **🧭 Description**                                                                           |
| ------------------ | ----------- | ------------------------------------------------------------------------------------------- |
| 📦 Dataset Item     | $0.0004     | Charged for each reply added to the dataset                                                 |
| 💬 Replies Query    | $0.014      | Charged for each query made using the default replies flow (`replies-query`)                |
| 🔎 Search Query     | $0.016      | Charged for each query made using the search-based flow (`useSearch: true`, `search-query`) |

#### 🎁 Free Results for Paying Users

On top of the per-item pricing, **paid-plan users get an additional free allowance per query, roughly the same size (~40 items) on either flow**: the first page of results is free on the default replies flow, and the first two pages are free on the search-based flow (`useSearch: true`) — the flows just use different page sizes. Dataset-item charges only start applying after that.

#### 💵 Understanding Your Costs

- **Single Tweet, default flow:** One `tweetIds` entry with `useSearch` off costs $0.014 for the replies query (`replies-query`). On a paid plan, the first page of replies (~40 items) is free — you're only charged $0.0004 per item once you go past it.
- **Single Tweet, search flow:** One `tweetIds` entry with `useSearch: true` costs $0.016 for the search query (`search-query`). On a paid plan, the first two pages (~40 items) are free — $0.0004 per item applies after that.
- **Batch run (10 Tweet IDs), default flow:** 10 replies queries (`replies-query`) cost 10 × $0.014 = $0.14, plus $0.0004 per item collected beyond each query's free first page (~40 items each).
- **Free Plan Demo run:** No separate query or item charges — capped at 10 items per run, up to 5 runs per month.

#### 🧭 Why It Works So Well

- ✅ **Pay per result**, with transparent per-item and per-query pricing.
- 🚀 Scale from a single-thread reply pull to ongoing brand-monitoring jobs seamlessly.
- 🎁 **Paid users** get ~40 free items per query on either flow — the first page on the default flow, or the first two pages on the search flow.
- 🆓 **Free Plan Demo Mode** lets you test the actor (5 runs/month, 10 items/run) before subscribing.

### 🆓 Demo Mode & Free Users

Users on the Free Plan can use the actor only in Demo Mode. Free users can run the actor up to **5 times per month**, with each run capped at a maximum of **10 items** — just enough to test it out. Paid-plan users are not subject to this cap and additionally get ~40 items free per query (the first page on the default flow, or the first two pages on the search-based flow). To use this actor without limitations, subscribe to a paid plan on Apify.

### 🍚 Input Parameters

The **Twitter Replies Scraper** offers streamlined configuration for extracting replies from any tweet — with flexible input methods and a powerful custom transformation option.

| **🧩 Field**       | **📝 Type** | **📖 Description**                                                                                         | **🪄 Default Value** |
| ----------------- | ---------- | --------------------------------------------------------------------------------------------------------- | ------------------- |
| startUrls         | Array      | Twitter (X) URLs to pull replies from. Required if `tweetIds` is empty.                                   | []                  |
| tweetIds          | Array      | Tweet IDs to pull replies from. Required if `startUrls` is empty.                                         | []                  |
| useSearch         | Boolean    | Switches reply fetching to the search-based `conversation_id:` flow instead of the default replies flow.  | false               |
| maxItems          | Number     | Maximum number of replies to receive as output. Leave empty for unlimited.                                | Infinity            |
| customMapFunction | String     | JavaScript function that reshapes, renames, or filters fields on every output row. Must return an object. | —                   |

#### ⚡ Supported Input Types

- 🔢 **Tweet IDs** — Direct numeric tweet identifiers (e.g., `1981345445986402472`)
- 🔗 **Tweet URLs** — Full X/Twitter status links (e.g., `https://x.com/Nike/status/1981345445986402472`)

📌 *Important: The target tweet must exist, be public, and have at least one reply. If the default flow returns fewer replies than expected, enable `useSearch` for broader coverage.*

### 🍜 Output

The **Twitter Replies Scraper** returns **comprehensive, structured JSON data** for every reply — full reply text, author profile, engagement metrics, and conversation context, ready to analyze or feed into your own pipeline.

#### 📦 Example Output Object

```json
{
    "type": "reply",
    "id": "1981347133442888040",
    "url": "https://x.com/Trueblue1123134/status/1981347133442888040",
    "twitterUrl": "https://twitter.com/Trueblue1123134/status/1981347133442888040",
    "text": "@Nike W",
    "fullText": "@Nike W",
    "source": "Twitter for Android",
    "retweetCount": 0,
    "replyCount": 0,
    "likeCount": 1,
    "quoteCount": 0,
    "viewCount": 147,
    "createdAt": "Thu Oct 23 13:09:02 +0000 2025",
    "lang": "und",
    "bookmarkCount": 0,
    "isReply": true,
    "inReplyToId": "1981345445986402472",
    "conversationId": "1981345445986402472",
    "inReplyToUserId": "415859364",
    "inReplyToUsername": "Nike",
    "author": {
        "type": "user",
        "userName": "Trueblue1123134",
        "url": "https://x.com/Trueblue1123134",
        "id": "1975160847581560834",
        "name": "Hello",
        "isVerified": false,
        "isBlueVerified": false,
        "followers": 14,
        "following": 97,
        "createdAt": "Mon Oct 06 11:27:05 +0000 2025",
        "favouritesCount": 15,
        "mediaCount": 6,
        "statusesCount": 55
    },
    "entities": {
        "user_mentions": [
            {
                "id_str": "415859364",
                "name": "Nike",
                "screen_name": "Nike"
            }
        ]
    },
    "isRetweet": false,
    "isQuote": false,
    "media": []
}
````

#### 🧭 Output Structure Highlights

| **🪄 Field**                        | **📖 Description**                                                          |
| ---------------------------------- | -------------------------------------------------------------------------- |
| id, text, fullText                 | Unique reply identifier and full reply text                                |
| retweetCount, likeCount, viewCount | Complete engagement metrics for performance analysis                       |
| conversationId, inReplyToId        | Thread context so you can rebuild the full conversation                    |
| author                             | Full author profile: username, followers, verification status, account age |
| entities                           | Mentions and other embedded entities within the reply                      |
| createdAt                          | Timestamp of the reply for temporal / trend analysis                       |
| url, twitterUrl                    | Direct links to the original reply on X and Twitter domains                |

All reply data exports in **JSON, CSV, Excel, XML, or RSS** — ready for immediate integration with CRMs, sentiment-analysis pipelines, data warehouses, or custom dashboards. Perfect for brand monitoring tools, audience research workflows, and lead-generation lists.

### Search Flow vs Replies Flow

By default, the actor uses the Twitter replies endpoint to retrieve replies directly.

When `useSearch` is enabled, the actor instead performs a Twitter search using:

```text
conversation_id:<tweetId>
```

Example:

```text
conversation_id:1981345445986402472
```

This method may return a broader set of conversation tweets and can sometimes retrieve results that are not available through the standard replies endpoint — useful when the default flow returns thinner results than you expect.

### 🍳 Custom Map Function

Use this function to reshape the output of every row you get back from this actor. It receives each row as an argument, so you can rename fields, change formatting, or pick only the attributes you want in the final output.

**The return value of this function has to be an object.**

Example:

```javascript
(object) => {
    return {
        username: object.author.userName,
        replyText: object.fullText,
        likes: object.likeCount + " likes",
    };
}
```

This example will:

- Add a new field `username`
- Add a new field `replyText`
- Reformat the like count into a new field `likes`

Result:

```json
{
    "username": "Trueblue1123134",
    "replyText": "@Nike W",
    "likes": "1 likes"
}
```

You can use the function to:

- Add new fields
- Change existing fields
- Select only the fields you want in the output

### 🔧 Troubleshooting & Common Issues

Encountering issues with the Twitter Replies Scraper? Below are solutions to common problems based on actual actor configuration and user feedback.

#### ❓ Getting Few Replies? (Low Result Count)

**Problem:** The scraper returns fewer replies than you expected to see on the tweet.

**Solution:** Check the **maxItems** field first — if it's set too low, the run stops early. Then try enabling **`useSearch: true`**. The search-based `conversation_id:` flow sometimes surfaces replies the default replies endpoint misses, especially on tweets with very large or old conversation threads.

Example configuration:

```json
{
    "tweetIds": ["1981345445986402472"],
    "useSearch": true,
    "maxItems": 500
}
```

#### 📂 Are Some Reply Fields Missing? (Incomplete Data)

**Problem:** Some output fields appear empty, or the Console preview doesn't show everything you expected.

**Solution:** The Apify Console preview only displays a subset of fields. To access the complete reply data:

- Navigate to the **"Storage"** tab in the Apify Console.
- Choose either **"Download the results"** (JSON, CSV, or Excel with all fields) or **"Open in a New Tab"** to view the full dataset in-browser.

#### ⚠️ Getting No Results? (Zero Data Returned)

**Problem:** The actor runs but returns 0 results.

**Solution:** Confirm that:

- The Tweet ID or URL is valid, public, and actually has replies. Test it manually on x.com first.
- You haven't mistyped the Tweet ID — copy it directly from the tweet URL.
- The tweet isn't from a protected/private account — only public tweets can be scraped.

Start with a known tweet that has plenty of replies to verify the scraper works, then move to your target tweets.

#### 🚨 Actor Run Failed or Shows Errors?

**Problem:** The actor stops with an error status or shows failure messages.

**Solution:** Check the **Log tab** in the Apify Console for specific error messages. Verify your input JSON syntax — invalid JSON causes immediate failure. Test with a minimal input (one Tweet ID, low `maxItems`) to isolate the issue.

#### 📧 Need Additional Help?

If you've tried the solutions above and still experience issues with reply scraping:

**Contact Support:** <apidojo10@gmail.com> — You name it, we get it.

### 🎯 Who Needs This Twitter Replies Scraper? (Use Cases & Industries)

The API Dojo **Twitter Replies Scraper** is a specialized **X reply data extraction tool** built for professionals who need structured, conversation-level intelligence. Whether you're focused on **brand monitoring**, **sentiment analysis**, **lead generation**, or **community discovery** — this **Twitter replies scraper** turns raw reply threads into actionable business insight.

#### 📢 Brand Monitoring & Social Listening Teams

**Use Twitter Replies Scraper to track how audiences respond to brand tweets in real time.** Social listening teams pull every reply to a brand's own posts, or to a campaign hashtag's top tweet, to catch complaints, praise, and viral moments early.

**Key capabilities:**

- Scrape replies to any brand or competitor tweet to monitor sentiment as it unfolds
- Extract reply author profiles to distinguish real customers from bots and spam accounts
- Track engagement metrics on replies to surface the most-amplified reactions
- Feed reply text directly into sentiment-analysis pipelines
- Monitor product-launch tweets for early customer feedback

**Example:** Scrape all replies to a product-launch tweet within the first 24 hours to flag negative sentiment spikes before they escalate into a PR issue.

#### 📊 Sentiment Analysis & Data Science Teams

**Use Twitter Replies Scraper for training and validating NLP sentiment models.** Data teams love the clean, structured reply output with full text, timestamps, and engagement fields ready to feed straight into a model pipeline.

**Key capabilities:**

- Scrape thousands of replies across many tweets to build labeled training datasets
- Extract engagement-weighted sentiment signals (likes/views per reply)
- Analyze reply language distribution (`lang` field) for multilingual sentiment models
- Combine reply text with author metadata for bot-detection features
- Track sentiment shifts across a conversation over time using `createdAt`

**Example:** Scrape 10,000 replies across 50 competitor product-announcement tweets to train a sentiment classifier tuned specifically for tech-launch reactions.

#### 🔍 Competitive Intelligence & Market Analysts

**Use Twitter Replies Scraper for competitor monitoring and audience-reaction benchmarking.** Analysts track how the market responds to a competitor's announcements, pricing changes, or product launches by scraping the replies underneath their tweets.

**Key capabilities:**

- Scrape replies to competitor announcement tweets to benchmark audience reaction
- Extract reply author follower counts to weight influential responses more heavily
- Track reply volume and engagement over time as a proxy for announcement impact
- Identify recurring complaints or praise themes across multiple competitor tweets
- Monitor conversation threads following price changes or feature releases

**Example:** Scrape replies to a competitor's pricing-change announcement to gauge customer backlash and inform your own positioning.

#### 💼 Lead Generation Specialists & B2B Sales

**Use Twitter Replies Scraper for B2B lead discovery inside relevant conversations.** Lead-gen professionals scrape replies to industry-relevant tweets to find people actively discussing pain points your product solves.

**Key capabilities:**

- Scrape replies to industry-thought-leader tweets to find engaged prospects
- Extract reply author bios and follower counts to qualify leads
- Identify users repeatedly replying to competitor tweets with complaints
- Build outreach lists from reply authors discussing specific pain points
- Track which accounts consistently engage with a given topic or hashtag conversation

**Example:** Scrape replies to a viral tweet about a common industry problem to build a targeted list of prospects already discussing that exact pain point.

#### 🏘️ Community Managers & Growth Teams

**Use Twitter Replies Scraper for community discovery and engagement analysis.** Community managers scrape replies to their own posts (or partner/collaborator posts) to find their most engaged followers and identify who to spotlight or reward.

**Key capabilities:**

- Scrape replies to owned content to identify top engaged community members
- Extract engagement metrics to rank the most valuable replies for reposting
- Track reply author growth (followers, following, join date) to spot rising community voices
- Identify spam or low-quality reply patterns to inform moderation rules
- Monitor reply sentiment on community announcements or AMAs

**Example:** Scrape all replies to a weekly community AMA thread to identify the most engaged members for a loyalty shout-out or ambassador program.

#### 🎓 Researchers & Academic Analysts

**Use Twitter Replies Scraper for social-media and discourse research.** Academic researchers use structured reply data to study conversation dynamics, misinformation spread, and public reaction to news events.

**Key capabilities:**

- Scrape replies at scale for discourse-analysis and conversation-structure studies
- Extract structured data on reply timing, volume, and author demographics
- Track how a conversation thread evolves over hours or days using `createdAt`
- Analyze mention networks (`user_mentions`) to map conversation participants
- Build longitudinal datasets tracking reactions to recurring news events

**Example:** Scrape replies to 200 news-outlet tweets covering the same event to study how public reaction differs by source and phrasing.

### 💡 How to Scrape Twitter Replies: Step-by-Step Guide

The **Twitter Replies Scraper** is designed for simplicity — whether you're pulling replies from a single tweet or monitoring dozens of conversations. Follow this guide to start scraping in minutes.

#### 🚀 Quick Start: 3 Steps to Scrape Twitter Replies

**Step 1: Choose Your Input Method**

The scraper accepts two input formats:

- **Tweet URLs:** Paste the full status link
  - Example: `https://x.com/Nike/status/1981345445986402472`
- **Tweet IDs:** Enter the numeric ID directly
  - Example: `1981345445986402472`

**Step 2: Configure Your Parameters**

Set your extraction preferences:

- **maxItems:** Control total replies collected (leave empty for unlimited)
- **useSearch:** Enable for broader, search-based conversation coverage
- **customMapFunction:** Reshape output fields with custom JavaScript (optional)

**Step 3: Run & Export**

Click "Start" and watch the scraper extract every available reply. Export results as JSON, CSV, Excel, XML, or RSS for immediate use in your workflows.

#### 📋 Method 1: Scrape Using Tweet URLs

**Best for:** Single conversations, manual lists, quick one-off pulls

```json
{
    "startUrls": [
        "https://x.com/Nike/status/1981345445986402472"
    ],
    "maxItems": 100
}
```

**Output:** Every available reply to that tweet, including full author profile and engagement metrics.

#### 📋 Method 2: Scrape Using Tweet IDs

**Best for:** Bulk operations, IDs pulled from another API or dataset

```json
{
    "tweetIds": [
        "1981345445986402472"
    ],
    "maxItems": 100
}
```

#### 🔎 Advanced: Use the Search-Based Flow for Broader Coverage

**Use case:** The default flow returns fewer replies than you expect, or you want to catch conversation tweets outside the standard replies endpoint

```json
{
    "tweetIds": [
        "1981345445986402472"
    ],
    "useSearch": true,
    "maxItems": 1000
}
```

**Result:** The actor searches `conversation_id:1981345445986402472` and returns a broader set of conversation tweets.

#### 🧪 Advanced: Reshape Output with a Custom Map Function

**Use case:** You only need a few fields, or you want them renamed to match your own schema

```json
{
    "tweetIds": ["1981345445986402472"],
    "maxItems": 100,
    "customMapFunction": "(object) => ({ username: object.author.userName, replyText: object.fullText, likes: object.likeCount })"
}
```

#### 🔧 Best Practices for Twitter Reply Scraping

**✅ DO:**

- **Verify the tweet exists and is public** before running a large job
- **Use reasonable maxItems** — start with 50-100 replies for testing
- **Enable useSearch** when the default flow underperforms on a specific tweet
- **Use customMapFunction** to keep only the fields your pipeline needs, cutting downstream processing
- **Test on the Free Plan's Demo Mode** before committing to a paid plan

**❌ DON'T:**

- **Scrape tweets with zero replies** — this wastes run time and returns nothing
- **Assume useSearch always returns more** — test both flows on your specific tweet before deciding
- **Use customMapFunction for filtering out required fields you'll need later** — keep a superset until you're sure of your schema
- **Scrape protected/private account tweets** — only public tweets are accessible

### ❓ Frequently Asked Questions (FAQ)

#### Can I scrape Twitter replies without a Twitter developer account?

Yes, this Twitter Replies Scraper extracts all public reply data without requiring an X/Twitter developer account, API key, or login.

#### How much does it cost to scrape replies from a tweet?

You pay $0.0004 per reply collected, plus $0.014 per query on the default replies flow (or $0.016 per query if you use the search-based flow). On a paid plan, the first page of results (~40 items) per query is free, so a 500-reply pull on the default flow costs roughly (500 - 40) × $0.0004 + $0.014 = $0.198 total.

#### What's the difference between the default flow and the search-based flow?

The default flow queries Twitter's replies endpoint directly. The search-based flow (`useSearch: true`) instead searches `conversation_id:<tweetId>`, which can surface a broader set of conversation tweets not always available through the standard endpoint.

#### Can I use both a Tweet ID and a Tweet URL in the same run?

Yes. You can populate both `tweetIds` and `startUrls` in the same input — the actor processes both lists.

#### Does this scraper work on the Apify Free Plan?

Yes, Free Plan users get **Demo Mode** — up to 5 runs per month, each capped at 10 items — enough to test the actor and validate output format before subscribing.

#### Can I extract reply author bio and follower data?

Yes, every reply includes a full `author` object with username, bio, follower/following counts, verification status, account creation date, and more.

#### Can I filter or reshape the output fields?

Yes, use the **customMapFunction** input to write a JavaScript function that renames, reformats, or selects only the fields you want in the final dataset.

#### What happens if I enter an invalid Tweet ID or URL?

Invalid or non-existent Tweet IDs/URLs return no results for that entry. The actor continues processing any other valid entries in your input. Check the Log tab for specific error messages.

#### Can I scrape replies to protected/private account tweets?

No, this scraper only accesses replies on public tweets. Protected or restricted accounts cannot be scraped.

#### How many replies can I scrape per run?

Set any value for **maxItems**, or leave it empty for unlimited extraction (subject to how many replies actually exist on the tweet).

#### Can I automate reply scraping on a schedule?

Yes, use Apify's built-in scheduler to run the actor automatically at set intervals — useful for ongoing brand monitoring or tracking reactions to a live campaign.

#### What data formats can I export?

Export scraped reply data in **JSON**, **CSV**, **Excel (.xlsx)**, **XML**, or **RSS**, or access it via the Apify API.

#### Can I rebuild the full conversation thread from the output?

Yes, each reply includes `conversationId`, `inReplyToId`, and `inReplyToUsername`, letting you reconstruct the thread structure from the flat dataset.

#### Does the scraper extract mentions and hashtags from replies?

Yes, the `entities` object includes `user_mentions` and other embedded entities found in each reply's text.

#### How accurate are the engagement metrics?

Metrics are extracted directly from Twitter/X at the moment of scraping and reflect the exact values shown on the platform at that time.

#### Can I use this for sentiment analysis pipelines?

Absolutely. The clean, structured `fullText` field per reply, combined with engagement metrics and timestamps, plugs directly into most sentiment-analysis or NLP pipelines.

#### Do I need proxies to scrape Twitter replies?

No, proxies are not required. The scraper runs reliably without any additional proxy setup or cost.

#### Why did my run return fewer replies than I see on the tweet itself?

This can happen with the default replies flow on very large threads. Try enabling `useSearch: true` to run the broader `conversation_id:` search flow, which sometimes surfaces additional replies.

### Contact

If you need any sort of support, please send an email to <apidojo10@gmail.com>. You name it, we get it.

# Actor input Schema

## `startUrls` (type: `array`):

Twitter (X) URLs. Required if tweetIds is empty.

## `tweetIds` (type: `array`):

Tweet IDs that you want to get replies on Twitter (X). Required if startUrls is empty.

## `useSearch` (type: `boolean`):

Determines whether reply fetching should use the search-based flow instead of the default replies flow.

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

Maximum number of items that you want as output.

## `customMapFunction` (type: `string`):

Function that takes each of the objects as argument and returns data that will be mapped by the function itself.

## Actor input object example

```json
{
  "startUrls": [
    "https://x.com/Nike/status/1981345445986402472"
  ],
  "tweetIds": [
    "1981345445986402472"
  ],
  "useSearch": false,
  "maxItems": 1000,
  "customMapFunction": "(object) => { return {...object} }"
}
```

# Actor output Schema

## `overview` (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 = {
    "startUrls": [
        "https://x.com/Nike/status/1981345445986402472"
    ],
    "tweetIds": [
        "1981345445986402472"
    ],
    "maxItems": 1000,
    "customMapFunction": (object) => { return {...object} }
};

// Run the Actor and wait for it to finish
const run = await client.actor("apidojo/twitter-replies-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 = {
    "startUrls": ["https://x.com/Nike/status/1981345445986402472"],
    "tweetIds": ["1981345445986402472"],
    "maxItems": 1000,
    "customMapFunction": "(object) => { return {...object} }",
}

# Run the Actor and wait for it to finish
run = client.actor("apidojo/twitter-replies-scraper").call(run_input=run_input)

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

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

```

## CLI example

```bash
echo '{
  "startUrls": [
    "https://x.com/Nike/status/1981345445986402472"
  ],
  "tweetIds": [
    "1981345445986402472"
  ],
  "maxItems": 1000,
  "customMapFunction": "(object) => { return {...object} }"
}' |
apify call apidojo/twitter-replies-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "command": "npx",
            "args": [
                "mcp-remote",
                "https://mcp.apify.com/?tools=apidojo/twitter-replies-scraper",
                "--header",
                "Authorization: Bearer <YOUR_API_TOKEN>"
            ]
        }
    }
}

```

## OpenAPI specification

```json
{
    "openapi": "3.0.1",
    "info": {
        "title": "Fast Twitter (X) Replies Scraper API",
        "description": "Extract every reply from any Twitter (X) post by Tweet ID or URL with full author data and engagement metrics (likes, replies, reposts, quotes, views). Optional search mode for broader coverage; export to JSON, CSV & Excel. Ideal for brand monitoring, sentiment analysis & competitor research.",
        "version": "0.0",
        "x-build-id": "cnkrX5tq93kdUAduS"
    },
    "servers": [
        {
            "url": "https://api.apify.com/v2"
        }
    ],
    "paths": {
        "/acts/apidojo~twitter-replies-scraper/run-sync-get-dataset-items": {
            "post": {
                "operationId": "run-sync-get-dataset-items-apidojo-twitter-replies-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        },
        "/acts/apidojo~twitter-replies-scraper/runs": {
            "post": {
                "operationId": "runs-sync-apidojo-twitter-replies-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor and returns information about the initiated run in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK",
                        "content": {
                            "application/json": {
                                "schema": {
                                    "$ref": "#/components/schemas/runsResponseSchema"
                                }
                            }
                        }
                    }
                }
            }
        },
        "/acts/apidojo~twitter-replies-scraper/run-sync": {
            "post": {
                "operationId": "run-sync-apidojo-twitter-replies-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        }
    },
    "components": {
        "schemas": {
            "inputSchema": {
                "type": "object",
                "properties": {
                    "startUrls": {
                        "title": "Start URLs",
                        "type": "array",
                        "description": "Twitter (X) URLs. Required if tweetIds is empty.",
                        "items": {
                            "type": "string"
                        }
                    },
                    "tweetIds": {
                        "title": "Tweet IDs",
                        "type": "array",
                        "description": "Tweet IDs that you want to get replies on Twitter (X). Required if startUrls is empty.",
                        "items": {
                            "type": "string"
                        }
                    },
                    "useSearch": {
                        "title": "Use Search",
                        "type": "boolean",
                        "description": "Determines whether reply fetching should use the search-based flow instead of the default replies flow.",
                        "default": false
                    },
                    "maxItems": {
                        "title": "Maximum number of items on output",
                        "type": "integer",
                        "description": "Maximum number of items that you want as output."
                    },
                    "customMapFunction": {
                        "title": "Custom map function",
                        "type": "string",
                        "description": "Function that takes each of the objects as argument and returns data that will be mapped by the function itself."
                    }
                }
            },
            "runsResponseSchema": {
                "type": "object",
                "properties": {
                    "data": {
                        "type": "object",
                        "properties": {
                            "id": {
                                "type": "string"
                            },
                            "actId": {
                                "type": "string"
                            },
                            "userId": {
                                "type": "string"
                            },
                            "startedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "finishedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "status": {
                                "type": "string",
                                "example": "READY"
                            },
                            "meta": {
                                "type": "object",
                                "properties": {
                                    "origin": {
                                        "type": "string",
                                        "example": "API"
                                    },
                                    "userAgent": {
                                        "type": "string"
                                    }
                                }
                            },
                            "stats": {
                                "type": "object",
                                "properties": {
                                    "inputBodyLen": {
                                        "type": "integer",
                                        "example": 2000
                                    },
                                    "rebootCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "restartCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "resurrectCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "computeUnits": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "options": {
                                "type": "object",
                                "properties": {
                                    "build": {
                                        "type": "string",
                                        "example": "latest"
                                    },
                                    "timeoutSecs": {
                                        "type": "integer",
                                        "example": 300
                                    },
                                    "memoryMbytes": {
                                        "type": "integer",
                                        "example": 1024
                                    },
                                    "diskMbytes": {
                                        "type": "integer",
                                        "example": 2048
                                    }
                                }
                            },
                            "buildId": {
                                "type": "string"
                            },
                            "defaultKeyValueStoreId": {
                                "type": "string"
                            },
                            "defaultDatasetId": {
                                "type": "string"
                            },
                            "defaultRequestQueueId": {
                                "type": "string"
                            },
                            "buildNumber": {
                                "type": "string",
                                "example": "1.0.0"
                            },
                            "containerUrl": {
                                "type": "string"
                            },
                            "usage": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "integer",
                                        "example": 1
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "usageTotalUsd": {
                                "type": "number",
                                "example": 0.00005
                            },
                            "usageUsd": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "number",
                                        "example": 0.00005
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    }
}
```
