Facebook Posts Search & Comments Scraper
Pricing
$19.99/month + usage
Facebook Posts Search & Comments Scraper
π Facebook Posts Search & Comments Scraper searches and extracts public Facebook posts by keyword, hashtag, or URLβcapturing text, author/page, timestamp, reactions, comments, shares, media & links. π Export CSV/JSON. Ideal for social listening, brand monitoring, trend & competitor analysis. π
Pricing
$19.99/month + usage
Rating
0.0
(0)
Developer
ScrapeBase
Maintained by CommunityActor stats
0
Bookmarked
14
Total users
2
Monthly active users
4 days ago
Last modified
Categories
Share
Facebook Posts Scraper β Extract Posts, Comments and Page Contacts
Facebook Posts Scraper searches public Facebook posts by keyword and returns typed JSON for three things in one run: the matching posts with full engagement data, each post's top-level comments in a separate dataset, and β when you switch it on β the business contact details (email, phone, website, address) behind the page that posted it. Unlike scraping frameworks that hand back raw HTML, it returns structured records ready for a spreadsheet, a database, or a model's context window without any parsing. A genuine absolute date-range filter is enforced on the saved dataset, not just logged, so out-of-range posts are never pushed or billed. This guide covers every input and output field and how monitoring, lead-gen, and research teams deploy it.
π§ What Does Facebook Posts Scraper Do?
Facebook Posts Scraper takes one or more keywords, runs a site:facebook.com search for each, and fetches every discovered post's public page directly β no Facebook login, session cookie, or Graph API access token required. It returns three linked layers of data: the post itself (engagement counts, text, media, page identity), that post's top-level comments (author, text, likes, replies) written to a separate uncharged child dataset, and, on request, the posting page's public contact card. Posts are filtered against an absolute dateFrom/dateTo window (or a rolling recency preset) before they are ever written to the dataset, so the numbers you see are the numbers you're billed for.
Key capabilities:
- Keyword-based post discovery β search Facebook by topic instead of needing a page URL up front
- Per-post engagement data β likes, comments, shares, post text, attached link, and thumbnail
- Child comment dataset β up to
maxCommentsPerPosttop-level comments per post, with author identity and like counts, in a dedicated uncharged dataset - Comment quality filtering and sorting β drop low-signal comments below a like threshold, or rank the kept ones most-liked-first
- Genuine absolute date filtering β
dateFrom/dateTorestrict what gets saved, not just what gets logged - Optional page contact/lead enrichment β pulls email, phone, website, and address from the posting page's own intro card
- Geo/language search targeting β bias Google's SERP discovery toward a specific country and language market
β‘ Features & Capabilities
The Actor's capabilities split into post discovery, comment collection, and optional lead enrichment β all delivered as one normalized schema per run.
Core features
- Multi-keyword search in one run β
keywordsaccepts a list; each keyword runs as an independent, concurrent search (asyncio.gatheracross queries) - Full engagement fields per post β
likesCount,commentsCount,sharesCount,postText,link,thumbnailUrl - Stable identifiers β
pageId,facebookId,postId,postFacebookIdextracted directly from Facebook's embedded page data, pluspostUrl/topLevelUrlfor the canonical permalink - Child comments dataset β
parentPostId-linked rows in a separatecomments-<runId>dataset that is never charged, capped atmaxCommentsPerPost - Post-fetch comment filtering β
minCommentLikesandsortCommentsByLikesoperate on comments already fetched, with no extra network calls and no fabricated counts - Page contact/lead enrichment β
enableContactLookupattaches anemail/phone/website/addressobject to every row, with missing fields returned asnullrather than guessed - Backward-compatible input β every renamed key (
keywords,maxPostsPerKeyword,recencyPreset,proxySettings) still accepts its original base-actor name (searchQueries,maxPosts,postTimeRange,proxyConfiguration) through a code-level fallback
Facebook Posts Scraper within the Scrapio data stack
Facebook Posts Scraper covers keyword-driven post discovery, top-level comments, and page contact enrichment. For deeper comment threads with nested replies on a specific post, photo, or reel, use Facebook-Comments-Scraper. For posts and comments scoped to a public Facebook Group instead of open keyword search, use facebook-groups-posts-scraper-with-author-engagement-analytics and facebook-groups-comments-replies-scraper. For lead capture centered on a single known page rather than keyword discovery, use facebook-page-posts-scraper-with-lead-contact-list.
Why do developers and data teams scrape Facebook?
π’ Social listening and keyword/topic monitoring
Marketing and PR teams feed keywords with a brand, product, or campaign name and collect every public post mentioning it, along with likesCount, commentsCount, and sharesCount to gauge reach, plus postText for message and sentiment review. The child comments dataset adds the public conversation underneath each mention β commentText and authorName per commenter β so a listening dashboard can show not just that a brand was mentioned, but how people reacted. Because dateFrom/dateTo genuinely restrict what's saved, teams can rerun the same keyword weekly and pull only the new window instead of re-processing a growing haystack.
π AI training data and RAG indexing
postText and commentText are this Actor's highest-information free-text fields β real, unstructured, publicly written language tied to a timestamp (postedAtTimestamp) and an engagement signal (likesCount), which makes them useful both for RAG indexing (index postText and top comments against postUrl as the citation source) and for fine-tuning data (pair postText with its comment thread as a document-and-reactions example). Every field returns as a typed primitive β strings, integers, booleans β so there's no HTML or markup to strip before it reaches an embedding pipeline or a training set.
π± Competitive and market intelligence
Point keywords at a competitor's name or product line and track sharesCount and commentsCount over successive scheduled runs to spot which posts are actually spreading versus which are quietly published and ignored. enableContactLookup additionally surfaces the competitor page's public website and email, useful for confirming which domain or storefront a campaign is actually driving traffic to.
π¬ Research and academic use
Communication and media researchers use keyword search to build corpora of public discourse around an event, hashtag-style topic, or public figure without needing page-by-page manual collection. Because the Actor only reaches content Facebook serves to a logged-out, unauthenticated request, the scope is inherently limited to public posts and comments β the same audience any visitor without an account would see.
π₯ Product and SaaS development
Teams building monitoring dashboards, lead-generation tools, or brand-analytics products use this Actor as the ingestion layer: run it on a schedule, write pageUrl, contact, and engagement fields into your own database, and layer your product's UI or scoring logic on top β no in-house scraping infrastructure to build or maintain.
π Input Parameters
All parameters are optional β the Actor runs with sensible defaults (a football keyword fallback) if keywords is left empty.
| Parameter | Required | Type | Description | Example Value |
|---|---|---|---|---|
keywords | No | array | Topics to search for on Facebook (site:facebook.com search). Each keyword runs as a separate, concurrent search. Same as base actor's searchQueries. | ["digital marketing", "SaaS onboarding"] |
maxPostsPerKeyword | No | integer | How many posts to collect per keyword (1β5000). Same as base actor's maxPosts. | 25 |
dateFrom | No | string | Only keep posts published on/after this date (YYYY-MM-DD). Leave blank to disable absolute filtering. | "2025-01-01" |
dateTo | No | string | Only keep posts published on/before this date (YYYY-MM-DD). Leave blank for no upper bound. | "2025-12-31" |
recencyPreset | No | string | Used only when dateFrom/dateTo are both blank. One of "", "24h", "7d", "30d", "90d". Same as base actor's postTimeRange. | "7d" |
maxCommentsPerPost | No | integer | Max top-level comments to fetch per post into the child dataset (0β500). 0 disables comment fetching. | 10 |
minCommentLikes | No | integer | Only keep fetched comments with at least this many likes. 0 (default) keeps all fetched comments. Applied after the maxCommentsPerPost cap. | 5 |
sortCommentsByLikes | No | boolean | When true, kept comments are sorted most-liked-first. Default false (original fetch order). | true |
targetCountry | No | string | Biases the Google SERP discovery toward a country (gl param). Blank = no bias. | "us" |
targetLanguage | No | string | Language for the search UI/results (hl param). Blank = default (English). | "es" |
enableContactLookup | No | boolean | When true, fetches each post's page and extracts public email/phone/website/address as a contact object. Default false. | true |
proxySettings | No | object | Proxy configuration for Facebook and Google requests. Same as base actor's proxyConfiguration. | {"useApifyProxy": true} |
Example input:
{"keywords": ["digital marketing", "SaaS onboarding"],"maxPostsPerKeyword": 25,"dateFrom": "2025-01-01","dateTo": "2025-12-31","maxCommentsPerPost": 15,"minCommentLikes": 5,"sortCommentsByLikes": true,"targetCountry": "us","targetLanguage": "en","enableContactLookup": true,"proxySettings": { "useApifyProxy": true }}
Supported URL types and input formats
This Actor is keyword-driven, not URL-driven β there is no direct "post URL" or "page URL" input field. Discovery always starts from a site:facebook.com search term, and any Facebook URLs the Actor visits are ones it finds itself via that search. Three real input patterns:
- Broad topic monitoring:
{"keywords": ["black friday deals"], "maxPostsPerKeyword": 100, "recencyPreset": "7d"}β recent posts on a topic, no comments. - Absolute-range research pull with comments:
{"keywords": ["climate policy"], "dateFrom": "2025-01-01", "dateTo": "2025-03-31", "maxCommentsPerPost": 50, "sortCommentsByLikes": true}β a fixed historical window with the most-liked comments per post. - Localized lead-gen sweep:
{"keywords": ["digital marketing agency"], "targetCountry": "gb", "targetLanguage": "en", "enableContactLookup": true}β UK-biased search results with page contact details attached.
π¦ Output Format
Each run writes to two datasets: the default dataset (one row per post, billed per row_result charged event) and a named child dataset comments-<runId> (one row per comment, never charged). Both export as JSON, CSV, Excel, XML, RSS, or an HTML table directly from the Apify Console or API β no extra configuration needed.
Output for Posts
{"pageUrl": "https://www.facebook.com/HubSpot","pageId": "175340385558135","pageName": "HubSpot","facebookId": "175340385558135","postId": "918273645192837","postFacebookId": "918273645192837","postUrl": "https://www.facebook.com/HubSpot/posts/918273645192837","topLevelUrl": "https://www.facebook.com/HubSpot/posts/918273645192837","postedAt": "2025-06-12 14:32:07","postedAtTimestamp": 1749738727,"likesCount": 842,"commentsCount": 96,"sharesCount": 51,"postText": "5 digital marketing trends we're tracking heading into Q3.","link": "https://www.facebook.com/HubSpot/posts/918273645192837","thumbnailUrl": "https://scontent.fplu2-1.fna.fbcdn.net/v/t39.30808-6/example_thumb.jpg","keyword": "digital marketing","contact": {"email": "info@hubspot.com","phone": "+1 888-482-7768","website": "https://www.hubspot.com","address": "2 Canal Park, Cambridge, MA"},"commentsFetched": 10,"scrapedAt": "2025-06-14T09:21:03.512481+00:00"}
contact is always present as an object; when enableContactLookup is off, or a field genuinely isn't found on the page, its members are null rather than omitted or guessed.
Output for Comments
{"parentPostId": "918273645192837","parentPostUrl": "https://www.facebook.com/HubSpot/posts/918273645192837","commentId": "Y29tbWVudDoxMjM0NTY3ODk=","feedbackId": "ZmVlZGJhY2s6OTE4MjczNjQ1MTkyODM3","commentUrl": "https://www.facebook.com/HubSpot/posts/918273645192837?comment_id=1234567890","commentDate": "2025-06-12T15:04:22+00:00","commentText": "Great breakdown, we've seen the same shift toward short-form video internally.","authorName": "Jordan Ellis","authorId": "100004521873629","authorProfileUrl": "https://www.facebook.com/jordan.ellis.94","authorProfilePicture": "https://scontent.fplu2-1.fna.fbcdn.net/v/t1.6435-1/example_profile.jpg","likesCount": 34,"repliesCount": 3,"threadingDepth": 0,"facebookCommentId": "1234567890","keyword": "digital marketing","isChild": true,"type": "comment","scrapedAt": "2025-06-14T09:21:04.118732+00:00"}
Comment rows are top-level comments only (no nested reply expansion), and commentsFetched on the parent post row tells you exactly how many comment rows exist for that post in the child dataset.
Schema stability and export options
Field names are extracted from Facebook's own embedded page and GraphQL data structures rather than from visual page layout, so they hold steady across Facebook's front-end redesigns better than a layout-based scraper would. Every renamed field also still accepts its original base-actor key on input, so pipelines built against either naming convention keep working after an upgrade. Both datasets support the full set of Apify's standard export formats β JSON, CSV, Excel, XML, RSS, and HTML table β with no separate delivery mechanism beyond the Apify dataset API.
π‘ Facebook Posts Scraper Strategy Guide
π― Strategy 1: Real-time enrichment pipeline
Trigger a run whenever your CRM or support system receives a new lead or brand mention: pass the lead's company name as a keywords entry with enableContactLookup: true and maxCommentsPerPost: 0 for a fast, comment-free pass. Read back pageUrl, likesCount, commentsCount, and the contact.email/contact.phone/contact.website fields, then write them onto the matching CRM record. Because the run returns typed JSON, no parsing step sits between the Actor and your database write.
π― Strategy 2: Scheduled monitoring and alerting
Use Apify's built-in Actor scheduler to run the same keywords list daily with recencyPreset: "24h" (or a rolling dateFrom set to yesterday). Keep a set of previously seen postId values from the prior run's dataset, diff the new run against it, and alert your team only on posts that are genuinely new and cross a likesCount or commentsCount threshold you define β rather than re-reviewing the full dataset every day.
π― Strategy 3: Bulk dataset build
For a research or training corpus, pass every keyword you need as a single keywords array β each entry runs as its own concurrent search within one Actor run (asyncio.gather under the hood), so a multi-topic pull doesn't require one run per keyword. Aggregate the default posts dataset and the child comments-<runId> dataset by postId/parentPostId and export both to CSV or a database table. No fixed concurrent-run limit is published for this Actor beyond the per-run maxPostsPerKeyword cap of 5000, so scale by widening the keyword list within a run rather than assuming an undocumented parallel-run ceiling.
Strategy comparison at a glance
| Strategy | Best for | Run pattern | Output format |
|---|---|---|---|
| Real-time enrichment | CRM/lead records needing live contact data | Single triggered run per lead, comments off | JSON written straight to CRM field |
| Scheduled monitoring | Ongoing brand/keyword alerting | Daily/weekly scheduled run, diffed against prior postIds | Dataset diff feeding an alert channel |
| Bulk dataset build | Research corpora, training data | One run, multi-keyword array, concurrent searches | Aggregated CSV or database table |
π΄ Related Facebook Scrapers & Tools
| Scraper Name | What it extracts |
|---|---|
Facebook-Comments-Scraper | Full comment threads with nested replies and commenter profiles for a specific post/photo/reel |
facebook-groups-posts-scraper-with-author-engagement-analytics | Posts from public Facebook Groups with author and engagement analytics |
facebook-groups-comments-replies-scraper | Comments and nested reply threads on Facebook Group posts |
facebook-page-posts-scraper-with-lead-contact-list | Posts and lead/contact data for one known Facebook Page (URL-driven, not keyword search) |
facebook-user-search-scraper-with-lead-contact-enrichment | Facebook profile/Page search results with contact-lead enrichment |
facebook-ads-library-scraper-advertiser-contact-finder | Meta Ad Library ads plus advertiser contact details |
linkedin-post-scraper-by-keyword | LinkedIn posts discovered by keyword search (cross-platform equivalent) |
extract-emails-contacts-socials-from-any-website-verified-phone-email-list | Contact enrichment for any external website your results link to |
How to integrate Facebook Posts Scraper with your stack
Facebook Posts Scraper works with any language or tool that can call the Apify API, most commonly through Apify's official apify-client SDKs for Python and Node.js.
Python
import csvfrom apify_client import ApifyClientclient = ApifyClient("<YOUR_APIFY_API_TOKEN>")keyword_batches = ["digital marketing", "SaaS onboarding", "b2b lead generation"]rows = []for keyword in keyword_batches:run_input = {"keywords": [keyword],"maxPostsPerKeyword": 25,"recencyPreset": "30d","maxCommentsPerPost": 5,"enableContactLookup": True,"proxySettings": {"useApifyProxy": True},}run = client.actor("Scrapio/facebook-posts-search-comments-scraper").call(run_input=run_input)for item in client.dataset(run["defaultDatasetId"]).iterate_items():rows.append(item)with open("facebook_posts.csv", "w", newline="", encoding="utf-8") as f:writer = csv.DictWriter(f, fieldnames=list(rows[0].keys()))writer.writeheader()writer.writerows(rows)print(f"Saved {len(rows)} posts across {len(keyword_batches)} keywords to facebook_posts.csv")
Node.js
import { ApifyClient } from 'apify-client';import fs from 'fs';const client = new ApifyClient({ token: '<YOUR_APIFY_API_TOKEN>' });const run = await client.actor('Scrapio/facebook-posts-search-comments-scraper').call({keywords: ['digital marketing', 'SaaS onboarding'],maxPostsPerKeyword: 25,maxCommentsPerPost: 10,enableContactLookup: true,});const { items } = await client.dataset(run.defaultDatasetId).listItems();fs.writeFileSync('facebook_posts.json', JSON.stringify(items, null, 2));console.log(`Saved ${items.length} posts to facebook_posts.json`);
Async and scheduled pipelines
Runs are asynchronous by default through the Apify API β start a run, poll client.run(runId).get() or wait on .call(), and pull results once status is SUCCEEDED. For recurring collection, use Apify's Actor scheduler to trigger runs on a cron-like schedule rather than polling manually, and use an Apify webhook on the ACTOR.RUN.SUCCEEDED event to have your own endpoint notified the moment a run's dataset is ready, instead of polling for completion.
π― Who Needs Facebook Posts Scraper? (Use Cases & Industries)
π’ Marketing and social listening teams
A marketing team tracking a product launch sets keywords to the campaign hashtag and product name, runs it daily, and watches sharesCount and the child comments dataset's commentText field for early sentiment β catching a negative thread while it's still small enough to respond to.
π AI/ML and RAG engineering teams
Teams building a support or research assistant index postText and commentText against postUrl as the source citation, giving the assistant real public-discourse context on a topic instead of relying on the model's training-time knowledge alone.
π± Competitive intelligence analysts
Analysts point the Actor at a competitor's name, track commentsCount/sharesCount trends run over run, and use enableContactLookup's website field to confirm which landing page a given campaign is actually funneling traffic to.
π¬ Researchers
Academic and market researchers assemble public-discourse datasets around an event or topic using keyword search alone, scoped entirely to what Facebook serves to a logged-out visitor β no account access, no private-group content.
π₯ Lead-generation and SaaS product builders
Teams building an outbound lead tool run keyword searches against an industry or niche term with enableContactLookup: true, and pipe the resulting pageName/contact records straight into their own scoring or outreach product without maintaining scraping infrastructure themselves.
Is it legal to scrape Facebook?
Scraping publicly accessible web data is generally lawful in the United States β the Ninth Circuit's hiQ Labs v. LinkedIn (9th Cir. 2019) held that scraping data a website makes available to logged-out visitors does not violate the Computer Fraud and Abuse Act. That precedent concerns public-data access, not Facebook's own Terms of Service: scraping still likely breaches Meta's ToS, which is a civil contract matter between you and Meta, not a criminal one. Separately, because this Actor can return commenters' names, profile URLs, and profile pictures, plus a page's business email, phone, and address when contact lookup is enabled, that output is personal data under GDPR and CCPA-style frameworks for any commenter or contact who is an identifiable individual. Facebook Posts Scraper returns only publicly accessible data. What you do with that data is your responsibility β consult legal counsel for commercial applications involving personal data.
β Frequently asked questions
Does Facebook Posts Scraper work without a Facebook account?
Yes. The Actor discovers posts through a Google search and fetches each post's public page directly over HTTP β no Facebook login, session cookie, or Graph API token is used or required anywhere in the code.
How does Facebook Posts Scraper handle Facebook's anti-scraping measures?
It routes search discovery through Apify's GOOGLE_SERP proxy group, the comment GraphQL calls through a residential proxy (falling back to your configured proxy), and Facebook page fetches through your proxySettings/Apify Proxy configuration. HTTP fetches retry with backoff on failure, and a failed comment or contact fetch for one post never aborts the run β it's logged and the post is still saved.
Can I run Facebook Posts Scraper at scale without getting blocked?
Multiple keywords in one run execute concurrently, and Apify Proxy rotation is applied per request rather than reused per run. No fixed request-rate or uptime figure is published for this Actor β scale gradually and monitor your run logs for blocked-request warnings rather than assuming an unlimited ceiling.
How fresh is the data Facebook Posts Scraper returns?
It's a live fetch every run β there is no caching layer. Each post is fetched fresh from Facebook at run time, and scrapedAt records the exact UTC timestamp of that fetch.
Does scraping Facebook comments violate Meta's Terms of Service?
Likely yes β Meta's Terms of Service prohibit automated data collection, and using this Actor to scrape Facebook is a potential breach of that contract regardless of whether the underlying public-data access is itself lawful. A ToS breach is a civil risk between you and Meta, separate from the criminal-law question addressed by cases like hiQ v. LinkedIn.
Which Facebook Posts Scraper fields work best for AI training and RAG indexing?
postText and commentText are the highest-information free-text fields for RAG indexing β pair either with postUrl/commentUrl as the citation source. For training data, the numeric and boolean fields (likesCount, commentsCount, sharesCount, threadingDepth) are the most structurally consistent across every row. All fields return as typed primitives, so no normalization step is needed before use.
Does Facebook Posts Scraper return personal data, and who is responsible for it?
Yes β comment authorName, authorId, and authorProfileUrl, and (when contact lookup is enabled) a page's public email, phone, and address, can constitute personal data for an identifiable individual. The Actor returns only what Facebook already serves publicly; establishing a lawful basis for storing, processing, or using that data sits with you as the operator, not with the Actor.
Does Facebook Posts Scraper work with Claude, ChatGPT, and other AI agent tools?
There is no dedicated MCP server for this Actor. It's callable as an HTTP endpoint by any agent framework through the Apify API or the apify-client SDK, and every response is typed JSON β an agent can pass the output directly into its context window with no HTML-parsing step in between.
Why might commentsFetched be lower than maxCommentsPerPost?
Two independent reasons, both disclosed rather than papered over: Facebook's comment GraphQL endpoint can be temporarily unreachable for a given post (in which case commentsFetched is 0 but the post row is still saved), or minCommentLikes filtered out comments that were fetched but fell below the like threshold. In either case the Actor never fabricates comments to make up the difference.
Does the page contact lookup work for personal profiles as well as business Pages?
No β enableContactLookup only fires when the discovered result resolves to a Facebook Page's own URL. Personal profile results are still returned with full post and engagement data, just with an empty contact object (null fields), since Facebook doesn't expose the same public intro/contact card on personal profiles.
βΉοΈ Disclaimer
Facebook Posts Scraper extracts only publicly available data from Facebook. This tool is intended for lawful use cases only. Users are responsible for complying with Facebook's Terms of Service and applicable data protection laws β including GDPR and CCPA where commenter or page contact details qualify as personal data β in their jurisdiction.
