Bluesky, Mastodon, Lemmy, Discourse and Tumblr
Posts from social networks and forums as typed JSON, every one in the same post shape, so feeds merge without mapping.
Posts from social networks and forums as typed JSON, every one in the same post shape, so feeds merge without mapping.
At a glance
Every endpoint here answers { endpoint, url, credits, duration_ms, data } with data as a SocialFeed: posts and next_cursor. Each post has the same fields whatever the site: id, url, author, author_name, title, text, created_at, likes, replies, reposts, tags, community, link and media. A count a site does not show is null. Send next_cursor back as cursor for the next page.
Endpoint | Typical |
|---|---|
| about 4.8 million posts per credit, up to 100 per call |
| about 1.4 million posts per credit, up to 100 per call |
| about 2.8 million posts per credit, up to 40 per call |
| about 2.3 million posts per credit, up to 50 per call |
| about 3.5 million posts per credit, up to 50 per call |
| about 7.5 million posts per credit, 50 per call |
| about 750,000 posts per credit, 20 per call |
| about 450,000 posts per credit, up to 20 per call |
| about 450,000 posts per credit, up to 20 per call |
- cURL
- Python
- Node.js
curl -G "https://api.scrapelyserp.com/v1/structured/bluesky/search" \
-H "Authorization: Bearer $SCRAPELY_API_KEY" \
--data-urlencode "query=web scraping" \
-d sort=latestimport os
import requests
HEADERS = {"Authorization": f"Bearer {os.environ['SCRAPELY_API_KEY']}"}
r = requests.get(
"https://api.scrapelyserp.com/v1/structured/bluesky/search",
headers=HEADERS,
params={"query": "web scraping", "sort": "latest"},
timeout=30,
)
r.raise_for_status()
data = r.json()
for p in data["data"]["posts"]:
print(p["created_at"], p["author"], p["text"][:80])const res = await fetch(`https://api.scrapelyserp.com/v1/structured/bluesky/search?${new URLSearchParams({ query: 'web scraping', sort: 'latest' })}`, {
headers: { Authorization: `Bearer ${process.env.SCRAPELY_API_KEY}` },
signal: AbortSignal.timeout(30_000),
});
if (!res.ok) throw new Error((await res.json()).error.code);
const data = await res.json();
for (const p of data.data.posts) console.log(p.created_at, p.author, p.text.slice(0, 80));Watching for mentions
A mention list does it for you: name a brand or a phrase, and every run searches Reddit, Bluesky, Lemmy and Tumblr newest first and sends each post you have not seen as watchlist.mention.found.
A handle, community, topic or server that does not exist (or is not public) is 404 NOT_FOUND, and a page we could not read is 502 TARGET_FAILED. Neither costs anything.
Bluesky
bluesky/search searches every public post; bluesky/posts is one account's posts, newest first, without its reposts of others.
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The search terms. |
|
|
| Result order. |
| integer |
| Posts per page, 1–100. |
| string | — | The |
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The account, e.g. |
| integer |
| Posts per page, 1–100. |
| string | — | The |
Full reference → GET /v1/structured/bluesky/search, GET /v1/structured/bluesky/posts
Mastodon
Public posts with a hashtag, on mastodon.social or any server you name with instance. A server also shows posts from the servers it federates with, so author always carries its server: name@server. reposts counts boosts.
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The hashtag, with or without |
| string |
| The Mastodon server to read, e.g. |
| integer |
| Posts per page, 1–40. |
| string | — | The |
Full reference → GET /v1/structured/mastodon/hashtag
Lemmy
lemmy/search searches posts; lemmy/posts is one community's. likes is the score (up votes less down votes), replies the comment count, community is name@server.
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The search terms. |
| string |
| The Lemmy server to read, e.g. |
| enum |
| Result order. |
| integer |
| Posts per page, 1–50. |
| string | — | The |
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The community, e.g. |
| string |
| The Lemmy server to read, e.g. |
| enum |
| Result order. |
| integer |
| Posts per page, 1–50. |
| string | — | The |
Full reference → GET /v1/structured/lemmy/search, GET /v1/structured/lemmy/posts
Discourse forums
Any public Discourse forum: name it with forum. discourse/search returns matching posts with their topic's title, tags and category (community), and an excerpt as text. discourse/topic returns a topic's posts in order, full text, the opening post first. A forum that needs a login is 404 NOT_FOUND.
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The forum’s domain, e.g. |
| string | — | The search terms. |
| string | — | The |
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The forum’s domain, e.g. |
| string | — | The topic’s id, e.g. |
| string | — | The |
Full reference → GET /v1/structured/discourse/search, GET /v1/structured/discourse/topic
Tumblr
tumblr/tagged is posts with a tag; tumblr/search searches by keyword. author is the blog, likes the likes (or notes), reposts the reblogs. Promoted posts are left out.
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The tag, e.g. |
|
|
| Result order. |
| integer |
| Posts per page, 1–20. |
| string | — | The |
Parameter | Type | Default | Description |
|---|---|---|---|
| string | — | The search terms. |
|
|
| Result order. |
| integer |
| Posts per page, 1–20. |
| string | — | The |
Full reference → GET /v1/structured/tumblr/tagged, GET /v1/structured/tumblr/search