Threads Account Replies Scraper
Pricing
from $0.99 / 1,000 results
Pricing
from $0.99 / 1,000 results
Rating
0.0
(0)
Developer
Farhan Febrian Nauval
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
9 days ago
Last modified
Categories
Share
Extract every reply a Threads user has posted to other people's threads — the full Replies tab, complete with the parent post each reply is answering — in a clean structured JSON output.
Why use this actor
- No account / no login required — just give it a Threads username or profile URL.
- No API key needed — Threads has no public consumer API; this actor returns the same data the web app shows on the Replies tab.
- Reply chain context — every record bundles the user's reply together with the original parent thread it answered, so you can see the conversation, not just the response in isolation.
- Engagement on replies — like counts, codes, and timestamps are returned per reply, so you can rank an account's most-engaged replies (a very different signal from their own posts).
- Bulk input — pass a list of usernames or URLs in one run; results stream straight into your dataset.
- Stable JSON output suitable for pipelines, spreadsheets, and databases — every row carries
_input,_source,_scrapedAtenvelope fields so you can join results back to your input list.
How it works
- You provide a list of Threads usernames (e.g.
mosseri) or full profile URLs. - The actor opens each profile, reads the public Replies tab, and paginates through it until it hits your
maxPostscap (or the end of the list). - For every reply it returns the reply post itself plus the parent thread it was answering, packaged in a flat JSON record.
- Results stream into your dataset, ready to download as JSON, CSV, or Excel.
You do not need to manage scrapers, browsers, or rotating IPs — all handled internally.
Input
{"usernames": ["mosseri","zuck"],"maxPosts": 30,"proxyConfiguration": {"useApifyProxy": true,"apifyProxyGroups": ["DATACENTER"]}}
| Field | Type | Description |
|---|---|---|
usernames | array | List of Threads usernames or full profile URLs to scrape. Both mosseri and https://www.threads.com/@mosseri are accepted. |
maxPosts | integer | Maximum replies returned per username. Default 30. Set to 0 for unlimited. |
proxyConfiguration | object | Apify Proxy settings. Datacenter proxy works for most cases; use Residential for very large batches. |
Output
Input: mosseri, maxPosts: 3
Each result is one reply chain: the parent thread the user was responding to, followed by the user's own reply. The example below shows two chains — Adam Mosseri (mosseri) replying to luizgcribeiro about the new Threads logo, then replying to theonion.
[{"_input": "mosseri","_source": "S1-primary","_scrapedAt": "2026-05-18T10:59:33.621591+00:00","id": "3897787543714767562","thread_items": [{"post": {"pk": "3897691905908415945","id": "3897691905908415945_63453918378","code": "DYXYiM3lh3J","taken_at": 1778861104,"like_count": 504,"caption": { "text": "new Threads logo swag just dropped" },"user": {"pk": "63453918378","username": "luizgcribeiro","is_verified": false,"profile_pic_url": "https://instagram.fcgk12-2.fna.fbcdn.net/v/t51.82787-19/632836115_..."},"image_versions2": { "candidates": [ { "height": 3024, "width": 4032, "url": "https://..." } ] },"text_post_app_info": {"reply_to_author": null,"is_post_unavailable": false,"share_info": { "quoted_post": null, "reposted_post": null }}},"line_type": "none","should_show_replies_cta": true,"__typename": "XDTThreadItem"},{"post": {"pk": "3897787543714767562","id": "3897787543714767562_63482099442","code": "DYXuR6hD6LK","taken_at": 1778872505,"like_count": 64,"caption": { "text": "👌🏼" },"user": {"pk": "63482099442","username": "mosseri","is_verified": true,"profile_pic_url": "https://instagram.fcgk12-1.fna.fbcdn.net/v/t51.82787-19/652081753_..."},"text_post_app_info": {"reply_to_author": { "username": "luizgcribeiro", "id": "63453918378" },"is_post_unavailable": false,"share_info": { "quoted_post": null, "reposted_post": null }}},"line_type": "none","should_show_replies_cta": true,"__typename": "XDTThreadItem"}]},{"_input": "mosseri","_source": "S1-primary","_scrapedAt": "2026-05-18T10:59:33.622601+00:00","id": "3895875287850949047","thread_items": [{"post": {"pk": "3895681172517134037","code": "DYQPWLeD57V","taken_at": 1778621410,"like_count": 203,"caption": { "text": "Celtics Attempt To Lure Giannis By Announcing Payton Pritchard His Brother Now https://theonion.com/..." },"user": { "pk": "63484314604", "username": "theonion", "is_verified": true },"text_post_app_info": { "reply_to_author": null, "is_post_unavailable": false }},"__typename": "XDTThreadItem"},{"post": {"pk": "3895875287850949047","code": "DYQ7e7dlBm3","taken_at": 1778644546,"like_count": 18,"caption": { "text": "love this" },"user": { "pk": "63482099442", "username": "mosseri", "is_verified": true },"text_post_app_info": {"reply_to_author": { "username": "theonion", "id": "63484314604" },"is_post_unavailable": false}},"__typename": "XDTThreadItem"}]}]
| Field | Type | Description |
|---|---|---|
_input | string | The username or URL exactly as you supplied it. Use this to join results back to your input list. |
_source | string | Internal tag for the path used to fetch the record. S1-primary means the fastest, richest path; values starting with S2- indicate a fallback was used. |
_scrapedAt | string | ISO-8601 UTC timestamp when the record was scraped. |
id | string | ID of the user's own reply (the last item in thread_items). |
thread_items | array | The full reply chain in chronological order. The last item is the user's reply; earlier items are the parent thread(s) being answered. |
thread_items[].post.pk | string | Numeric post ID for that item in the chain. |
thread_items[].post.code | string | Short URL slug; the full post URL is https://www.threads.com/@<user>/post/<code>. |
thread_items[].post.taken_at | integer | Unix timestamp (seconds) when the post was published. |
thread_items[].post.like_count | integer | Number of likes on that specific item. |
thread_items[].post.caption.text | string | The post's text body. null if it is an image-only post. |
thread_items[].post.user.username | string | Author handle of that item. Match this to your input username to identify which row is the user's own reply. |
thread_items[].post.user.pk | string | Numeric user ID of the post's author. Stable across handle changes. |
thread_items[].post.user.is_verified | boolean | true if the author has a verified badge. |
thread_items[].post.image_versions2.candidates | array | Image renditions attached to the post (multiple sizes from 150px up to original). Empty when the post is text-only. |
thread_items[].post.video_versions | array | Video renditions; null for non-video posts. |
thread_items[].post.carousel_media | array | Carousel slides; null when the post is single-media or text-only. |
thread_items[].post.text_post_app_info.reply_to_author | object | If this item is itself a reply, the parent author's username + numeric id. null on top-level posts. Use this field to walk the conversation chain. |
thread_items[].post.text_post_app_info.share_info.quoted_post | object | Populated when the item quotes another thread; otherwise null. |
thread_items[].post.text_post_app_info.share_info.reposted_post | object | Populated when the item is a repost; otherwise null. |
thread_items[].post.text_post_app_info.is_post_unavailable | boolean | true if the parent thread was deleted or hidden but the reply still references it. |
Error envelope
Profiles that can't be resolved or replies that fail to load return a structured error instead of crashing the run:
{"_input": "this-user-does-not-exist-xyz","_source": "S2-fallback","_error": "user_resolve_failed","_scrapedAt": "2026-05-18T10:59:34.000000+00:00"}
Filter on _error to triage failed rows. Common values: user_resolve_failed (the username does not exist or is private) and fetch_failed (the Replies tab could not be loaded — usually transient).
Pricing
This actor is billed per result: $6.00 per 1,000 reply chains (Tier 4). Each reply chain returned = 1 result. Error rows (user_resolve_failed, fetch_failed) are not billed.
Other Sosmed Actors
| Platform | Actor | Best for |
|---|---|---|
| Threads | Threads Account Scraper | Profile data (bio, followers, verified) for a Threads handle |
| Threads | Threads Account Threads Scraper | The user's own posts (Threads tab, not replies) |
| Threads | Threads Post Detail Scraper | Full conversation tree under any single thread URL |
| YouTube | YouTube Video Comments Scraper | Comment threads on any public YouTube video |
| Reddit User Profile Scraper | Karma, posts, trophies for any Reddit account | |
| X / Twitter | X Account Tweets Scraper | Latest tweets from any public X handle |
| Bluesky | Bluesky Post Detail Scraper | Replies and quotes under any Bluesky post |
Browse the full catalog at apify.com/xtracto.
Notes
- Only public replies are returned. If the account is private, the run yields a single
_error: "user_resolve_failed"row for that username. - Parent threads inside
thread_itemsmay be deleted or hidden by the time of scraping; in that case the parent'stext_post_app_info.is_post_unavailableistrueand the parent author's content fields may be empty. The user's own reply is still returned. - Conversation chain depth varies. Most reply chains are 2 items long (parent + reply), but threads with nested context can return 3+ items in
thread_items— always treat the last item as the user's own reply and earlier items as ancestors. - The numeric
pkand theuser.pkare the most reliable identifiers — Threads handles can be changed, but these numeric IDs do not. - For large jobs (>200 usernames), switch
proxyConfiguration.apifyProxyGroupsto["RESIDENTIAL"]to avoid per-IP rate limits.