Mastodon $1💰 URL, Trend & Profile Scraper
Pricing
from $1.00 / 1,000 results
Mastodon $1💰 URL, Trend & Profile Scraper
From $1/1K. Scrape trending Mastodon profiles and related posts from any Mastodon instance. Returns rich profile data, follower counts, bios, avatars, fields, and thread replies. Supports nested profile reviews or flat review output.
Pricing
from $1.00 / 1,000 results
Rating
0.0
(0)
Developer
Abot API
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
3 days ago
Last modified
Share
Mastodon Explore Scraper
Pull the trending profiles and their content from any Mastodon instance's explore page, straight from the public Mastodon API. You get rich profile records (bio, follower counts, fields, avatar) and their reviews, where a review is a post or a reply in its thread. Choose between profiles with reviews nested inside, a flat stream of reviews, or bulk posts by keyword. Defaults to mastodon.social and works on any Mastodon server.
Why this scraper
- Three output modes: trending profiles with nested reviews, reviews only (one flat record each), or keyword posts in bulk.
- Keyword mode harvests posts by topic at volume: each keyword timeline is walked back via load-more pagination up to your post cap (tens of thousands of posts).
- Reviews cover both a profile's own posts and the replies underneath them, so you capture the full conversation.
- Deep history: pull up to thousands of a profile's past posts, walked automatically via load-more pagination.
- Reads the public Mastodon REST API directly: fast, stable JSON, no fragile page parsing.
- Trending profiles merge two signals: authors of currently trending posts and the active public directory.
- URL mode: paste profile or post links to scrape exactly what you want.
- Works on any instance (mastodon.social, mas.to, fosstodon.org, your own server).
- Every record keeps the full upstream account object, so no field is ever dropped.
Data you get
Profile record (profiles mode):
| Field | Example |
|---|---|
| recordType | profile |
| id | 13179 |
| acct | Mastodon |
| username | Mastodon |
| displayName | Mastodon |
| bio | Free, open-source decentralized social media. Not for sale. |
| followersCount | 853000 |
| followingCount | 4 |
| statusesCount | 700 |
| url | https://mastodon.social/@Mastodon |
| avatar | https://files.mastodon.social/accounts/avatars/000/013/179/original/...png |
| bot | false |
| createdAt | 2016-11-23T00:00:00.000Z |
| fields | [{"name": "Homepage", "value": "joinmastodon.org"}] |
| reviewCount | 5 |
| reviews | [ ... array of review records ... ] |
Review record (reviews mode, keyword mode, or nested under a profile):
| Field | Example |
|---|---|
| recordType | review |
| id | 109876543210987654 |
| reviewType | post (or reply) |
| isReblog | false |
| rebloggedByAcct | null (set to the booster's handle when isReblog is true) |
| sourceKeyword | news (keyword mode only; null otherwise) |
| contentText | We just shipped a new version with quote posts. |
| createdAt | 2026-05-20T14:03:11.000Z |
| language | en |
| url | https://mastodon.social/@Mastodon/109876543210987654 |
| repliesCount | 42 |
| reblogsCount | 318 |
| favouritesCount | 901 |
| inReplyToId | null |
| tags | ["mastodon", "fediverse"] |
| authorAcct | Mastodon |
| authorDisplayName | Mastodon |
| account | { ... full upstream account object ... } |
How to use
Trending profiles with their reviews (default):
{"mode": "profiles","instanceUrl": "https://mastodon.social","profileSource": "both","includeReplies": true,"maxProfiles": 10,"maxReviewsPerProfile": 5,"maxRepliesPerPost": 10}
Reviews only, capped at 200, no replies (faster and cheaper):
{"mode": "reviews","profileSource": "trending","includeReplies": false,"maxProfiles": 20,"maxReviewsPerProfile": 10,"maxReviews": 200}
Bulk posts by keyword (high volume, load-more pagination):
{"mode": "keyword","keywords": ["news", "art", "climate"],"includeReplies": false,"maxPosts": 5000}
Deep history of one profile (thousands of past posts):
{"mode": "reviews","urls": ["https://mastodon.social/@Mastodon"],"includeReplies": false,"maxReviewsPerProfile": 2000}
Active local directory profiles only:
{"mode": "profiles","profileSource": "directory","onlyLocal": true,"maxProfiles": 25}
URL mode (specific profiles and posts):
{"mode": "reviews","urls": ["https://mastodon.social/@Mastodon","https://mastodon.social/@Gargron","https://mastodon.social/@Mastodon/109876543210987654"],"includeReplies": true}
Input parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
| mode | string | profiles | profiles (nested reviews), reviews (flat), or keyword (bulk posts by topic) |
| instanceUrl | string | https://mastodon.social | Any public Mastodon server |
| profileSource | string | both | trending, directory, or both (used when no URLs) |
| onlyLocal | boolean | false | Directory: local accounts only |
| urls | array | [] | Profile or post URLs; when set, overrides explore/profiles/reviews/keyword |
| keywords | array | [news] | Keywords to bulk-scrape in keyword mode (matched as tags, with or without #) |
| includeReplies | boolean | true | Fetch the reply thread under each post |
| maxProfiles | integer | 10 | Max profiles to scrape (up to 500) |
| maxReviewsPerProfile | integer | 5 | Posts to fetch per profile, walked via load-more (up to 5000) |
| maxRepliesPerPost | integer | 10 | Replies to keep per post |
| maxReviews | integer | 0 | Reviews-mode total cap (0 = unlimited) |
| maxPosts | integer | 500 | Keyword-mode total cap, split across keywords (up to 100000) |
| resumeFromRunId | string | (none) | Continue one specific interrupted run/dataset without re-collecting or re-charging |
| incrementalMode | boolean | false | Turn on for recurring monitoring; see "Resume & recurring updates" above |
| stateKey | string | (auto) | Name or share an incremental-mode monitoring campaign explicitly |
| emitUnchanged | boolean | false | Also return UNCHANGED records (incremental mode only; bills extra rows) |
| emitExpired | boolean | false | Also return EXPIRED records (incremental mode only; bills extra rows) |
| proxy | object | Apify datacenter | Proxy configuration |
Resume & recurring updates
Two different things, both optional:
- Resume from a previous run (
resumeFromRunId): paste a previous run ID or dataset ID to continue an interrupted crawl without returning or re-charging for records already collected there. - Incremental mode (
incrementalMode): turn this on for daily/weekly recurring monitoring of the same search. The actor remembers its own baseline (keyed by mode + instance + your query/filter settings, excluding themax*depth caps) in a key-value store — no run/dataset id to paste. The first run returns everything asNEW. Later runs return onlyNEW,UPDATED, andREAPPEAREDrecords by default. Turn onemitUnchangedoremitExpiredonly if you also want those rows back (and billed — they're extra dataset items).
When incrementalMode is on, every pushed record gains four fields:
| Field | Meaning |
|---|---|
| changeType | NEW, UPDATED, UNCHANGED, REAPPEARED, or EXPIRED |
| changedFields | Which fields differed from the last run (empty for NEW/UNCHANGED/REAPPEARED/EXPIRED) |
| firstSeenAt | When this record was first observed by this monitoring campaign |
| lastSeenAt | When this record was last observed |
EXPIRED rows (records that were present before but are no longer found) are only produced once a run has fully scanned its tracked scope — never when a cap, a failed page, an instance hiccup, or Resume cut a run short, since a partial scan can't tell "gone" apart from "not reached yet".
What counts as a real change vs. noise: followersCount/followingCount/statusesCount on a profile, and favouritesCount/reblogsCount/repliesCount on a top-level review/keyword-mode record, are genuinely volatile but treated as real data — a profile gaining a follower, or a trending post picking up favourites, is exactly what a recurring run should report. The same engagement counters on a review nested inside a profile record (profiles mode) are excluded from change detection there only — a nested post's favourite ticking would otherwise flag the whole profile UPDATED on every run and drown out real profile-level changes (bio, avatar, display name). A reply/post-listing fetch that fails outright never corrupts the baseline: the affected fields carry forward from the last successful scrape instead of being read as "this profile now has zero posts".
Use State key to name a monitoring campaign explicitly, or to intentionally share state across two differently-configured runs; leave it empty to let the actor derive one automatically so different searches never collide.
Send results into your apps (MCP connectors)
Optionally pipe the scraped results into the apps you already use, via Model Context Protocol (MCP) connectors. This is an extra delivery step after the scrape — the Apify dataset is never changed.
What gets written to the connector: a condensed, human-readable summary of each record — not the full JSON. Each item becomes one entry with a title and its key fields flattened to plain text. The complete record always stays in the Apify dataset.
- Authorize a connector once under Apify → Settings → Integrations (Notion, Linear, Airtable, or Apify).
- Select it in the "Pipe results into your apps" input field. (If the picker is empty, you haven't authorized a connector yet.)
- For Notion, also set
notionParentPageUrlto the page where items should be created.
The connection is mediated by Apify's MCP proxy, so this actor never sees your third-party credentials. Leave the field empty to skip.
Output example
{"recordType": "profile","id": "13179","acct": "Mastodon","username": "Mastodon","displayName": "Mastodon","bio": "Free, open-source decentralized social media. Not for sale.","followersCount": 853000,"followingCount": 4,"statusesCount": 700,"url": "https://mastodon.social/@Mastodon","bot": false,"createdAt": "2016-11-23T00:00:00.000Z","fields": [{ "name": "Homepage", "value": "joinmastodon.org" }],"reviewCount": 2,"reviews": [{"recordType": "review","id": "109876543210987654","reviewType": "post","contentText": "We just shipped a new version with quote posts.","createdAt": "2026-05-20T14:03:11.000Z","repliesCount": 42,"reblogsCount": 318,"favouritesCount": 901,"url": "https://mastodon.social/@Mastodon/109876543210987654","authorAcct": "Mastodon"},{"recordType": "review","id": "109876543299990000","reviewType": "reply","contentText": "Congrats, this is huge for the fediverse!","createdAt": "2026-05-20T14:09:55.000Z","inReplyToId": "109876543210987654","authorAcct": "someuser"}]}
Plan requirement
Runs on any Apify plan, including the free tier. The default connection works on every plan. A residential proxy connection is optional and only worth turning on for very large or sustained runs.