Facebook Groups Scraper - Facebook Group Posts, No Login avatar

Facebook Groups Scraper - Facebook Group Posts, No Login

Pricing

from $2.50 / 1,000 posts

Go to Apify Store
Facebook Groups Scraper - Facebook Group Posts, No Login

Facebook Groups Scraper - Facebook Group Posts, No Login

Facebook groups scraper, no login: public group links, ids or names in, one row per post out. Text, time, reactions by type, comments, shares, the author's public name and link, media, the post link and the group's exact member count. Free date window. Find groups by keyword. Misses free.

Pricing

from $2.50 / 1,000 posts

Rating

0.0

(0)

Developer

Hyperbach

Hyperbach

Maintained by Community

Actor stats

0

Bookmarked

4

Total users

3

Monthly active users

2 days ago

Last modified

Security

Limited permissions

Share

Facebook group posts as data, logged out. Give public group links (or a group's numeric id or name), or a single group post's link, and get one row per post: the whole text, the time to the second, the exact reactions by type, the comment and share counts, the author's public name and link, the photos and videos, the shared post, the post's link and its feedback id, and the group's exact member count on every row. Four orders (new posts, recent activity, top posts, listings), a free date window, filters by words and author, and up to 10 comments a post. Or give words and find public groups with their member count and privacy. Every input ends with a free row that says what was read and why it stopped. No login, no cookies, no browser, proxies handled for you.

From $5.00 per 1,000 rows (post) on the Free plan, $4.00 on Starter; every row and add-on is priced under Pricing below. A run start is $0.0045. The default input returns about 21 rows for about $0.1045. A private, missing or empty group is a free row that names its state, with the group's facts: you never pay for a group that gave no post.

Tested head-to-head on 2026-11-05

The job: the newest 20 posts of one public Facebook group by its link (Self-Taught Programmers, the schema's example input), new posts first. Every Actor ran on it the same day from the same harness; a rival's cost is what a buyer account paid, this Actor's is its list price on the Free plan. Fields counts the filled fields of a typical row. The lane's #2 by users/30d (datahamster/facebook-groups-search) finds groups by keyword and reads no group's posts: left out; the next group-posts seller by users/30d is curious_coder/facebook-post-scraper. Re-measured monthly.

ActorRowsFirst rowRun timeCostFieldsFailures
this Actor2011 s18 s$0.1042none
apify/facebook-groups-scraper2030 s39 s$0.08119none
curious_coder/facebook-post-scraper205.4 s9.8 s$0.02112none

Why this Facebook groups scraper

  • No charge for an empty, private or missing group. A private group, a group id that does not exist, an empty group or a link that names no group gets one free row with its status (private, not_found, invalid_input) and the reason, checked on a second connection before it says not_found. The lane's buyers report being charged for empty items; here only a delivered post or a found group is charged.
  • The date window is free. onlyPostsNewerThan and onlyPostsOlderThan cost nothing extra (the lane leader prices its date filter as an add-on), and every row is checked against the window before it is delivered: a post outside it is never charged. In the new-posts order the walk stops at the window's older end.
  • The group's facts on every row. One About page a group gives the exact member count ("373,967 total members", never the rounded "374K"), the privacy, the posts of the last day and the last month, the new-members line, the created date, the description and the rules on the group's row, and the member count and privacy on every post row.
  • No silent short lists. The walk goes to Facebook's own end of the list and asks the end again on a second connection before it calls the group COMPLETE; every group's row says COMPLETE, CAPPED, DATE_LIMIT or PARTIAL with the reason, how many posts were read, and the cursor where it stopped.
  • The author's link and the post's feedback id. The author's public profile link where Facebook links it in the group, and the post's feedback_id, which our Facebook Comments Scraper takes to read every comment and reply of the post.
  • Find groups by keyword. searchQueries lists public groups for your words, each with its exact member count, privacy and activity, in a web index's order (Facebook's own group search is closed to a logged-out reader); filter by privacy and member range for free.
  • Speed, measured. On 16 runs of version 0.1.7 on Apify (2026-11-05, 512 MB: the deploy gate, five cost runs, a 300-post walk and the head-to-head run below) the first post came 2.9 to 9.7 seconds after the Actor started (each group's About page is read first, for its exact member count); a group's newest 20 posts were out by 10.7 to 18.5 seconds, 50 posts by 22.5, and one group's 300 posts by 169 seconds. The head-to-head card counts from the run's start request, the container's start included: 11 seconds to the first row on its run, 7.3 by the Actor's own clock.

Who it's for

  • Community and market researchers — the posts of the groups where a topic is discussed, with their reactions, comments and the authors' public names, inside a date window, for a corpus or a trend report.
  • Brand, product and support teams — the newest posts of a list of groups each morning (onlyPostsNewerThan set to 1 day), filtered by a product or brand name with textContains.
  • Lead and partnership teams — groups about a keyword with their exact member counts and activity (searchQueries, minMembers), then their newest posts.

Quick start

A group's newest 20 posts

{
"startUrls": [
"https://www.facebook.com/groups/selftaughtprogrammers/"
],
"resultsLimit": 20
}

Two groups, the last week's posts, with comments

{
"startUrls": [
"https://www.facebook.com/groups/selftaughtprogrammers/",
"https://www.facebook.com/groups/874728723021553/"
],
"resultsLimit": 100,
"onlyPostsNewerThan": "7 days",
"maxCommentsPerPost": 5
}

Find groups by keyword

{
"searchQueries": [
"maths formulas"
],
"maxGroupsPerQuery": 10,
"groupPrivacy": "public"
}

Switching from apify/facebook-groups-scraper?

Your input works as it is. Each name in the left column is read as this Actor's own field and the run log says so (read <theirs> as <ours>); a name marked not read is ignored with a note. A value in the other Actor's shape, an object list or its own date form, is read too.

apify/facebook-groups-scraperthis Actorwhat to know
startUrlsstartUrlsThe same name and shape: group links as strings or as {"url": …} items; a group's numeric id or name works too.
resultsLimitresultsLimitThe same name: posts per group. Unset here means 20; 0 means every post.
viewOptionviewOptionThe same name and the same four values: CHRONOLOGICAL, RECENT_ACTIVITY, TOP_POSTS, CHRONOLOGICAL_LISTINGS.
onlyPostsNewerThanonlyPostsNewerThanThe same name and forms: a date, a time or a span such as 7 days.

What differs:

  • resultsLimit is 20 when you do not set it; 0 reads every post the group's feed serves.
  • The date window (onlyPostsNewerThan, and onlyPostsOlderThan, which the leader does not have) is free here; the leader prices its date filter as an add-on.
  • The output columns are snake_case (likes, comments, shares, group_name, author_name, media) where the leader's are camelCase (likesCount, commentsCount, sharesCount, groupTitle, user.name, attachments); each field's description names the leader's key.
  • Each input gets a free summary row (record_type = target) beside its post rows; filter on record_type = post for the posts alone.
  • A private, missing or empty group is a free row here, never a charged empty item.

Output

One row per post (and one free summary row for every input):

fieldmeaning
record_typepost on a post row (charged); group on a group a search found (charged); target on an input's free summary row (a group, a post link or a search you gave).
statusok, or why an input gave no row: not_found (no group or post by that link, id or name: Facebook answers an empty record or "This content isn't available" on two connections), private (a private group: only its members can see its posts; the row still carries the group's facts), invalid_input (a value that is not a Facebook group, group post or search, an empty value), duplicate (the same group as another value of the run, such as a group's name and its numeric id: its posts are on that value's rows), failed (Facebook refused every connection tried; run it again later), not_read (maxItems, your charge limit or the time limit came first).
inputThe value you gave that this row answers (the leader's inputUrl).
post_idFacebook's id of the post (the leader's legacyId).
urlThe post's own link, https://www.facebook.com/groups/<group>/posts/<id>/ (the leader's url).
feedback_idFacebook's id of the post's reactions and comments (the leader's feedbackId). Give it to our Facebook Comments Scraper for every comment and reply of the post.
post_typephoto, album, video, reel, link (a link with its preview), shared (a shared post), listing (a buy-and-sell listing, listing has its fields), text, event or other, read from the post's attachment, never guessed from the text.
is_videoTrue when the post carries a video or a reel.
is_shareTrue when the post shares another post (shared_post has it).
timeWhen the post was published, UTC, to the second (the leader's time).
timestampThe same time as Unix seconds.
video_publish_timeWhen the video of a video post was uploaded, UTC (usually a minute before time). Null on other posts.
textThe post's whole text, never cut (the leader's text); empty when the post has none (a photo alone, a share without words).
text_lengthThe text's length in characters.
hashtagsThe hashtags of the text, without #, in order, each once.
mentionsThe people, pages, groups and apps the text tags, as Facebook publishes them with the post: type, id, name, url (the leader's textReferences).
links_in_textThe links written in the text, unwrapped from Facebook's redirect.
author_idThe id of the member or page that posted (the leader's user.id).
author_nameThe author's public name as Facebook shows it (the leader's user.name).
author_urlThe author's public profile link where Facebook links it in the group (63 % of posts on ordinary groups, stage 2), never built from the id; null otherwise.
author_typeFacebook's own type for the author: user (a member; also a page in Facebook's new pages experience), page, group (a post by the group itself) or anonymous (a member who posted anonymously: the name is the one Facebook shows).
reactionsAll reactions, exact (the leader's likesCount).
likesThe same as reactions (all reaction types, not only Like).
reaction_types_countHow many reaction types the post has (the leader's topReactionsCount).
reactions_likeLike reactions, exact; 0 when none (the leader's reactionLikeCount).
reactions_loveLove reactions; 0 when none.
reactions_careCare reactions; 0 when none.
reactions_hahaHaha reactions; 0 when none.
reactions_wowWow reactions; 0 when none.
reactions_sadSad reactions; 0 when none.
reactions_angryAngry reactions; 0 when none.
commentsThe post's comment count as Facebook gives it, replies included (the leader's commentsCount).
sharesThe post's share count (the leader's sharesCount).
video_viewsVideo views (Facebook's video_view_count), exact. Null on a post with no video.
video_playsVideo plays (Facebook's play_count), exact, when Facebook gives it. Null otherwise.
video_post_viewsViews of the video in this post (Facebook's video_post_view_count), when given.
mediaThe post's photos and videos, in order (the leader's attachments): type (photo or video), id, url (the full-size photo or the video's page), width, height, alt_text (Facebook's description of a photo, the leader's ocrText), video_hd_url, video_sd_url, thumbnail_url, duration_s. The file links are Facebook's own and stop working after some days.
media_countHow many photos or videos the post holds (an album's or a listing's own count, which can be more than media lists).
media_truncatedTrue when the post holds more photos than media lists: Facebook sends a logged-out reader at most 5 photos of an album or a listing.
video_captions_urlThe video's captions file (.srt) when Facebook has one; null otherwise.
linkA link post's preview: url (the target, unwrapped), title, description, domain, image_url. Null on other posts.
eventAn event post's event: id, name, url, when, place. Null on other posts.
shared_postThe post this post shares: post_id, url, author_name, author_id, author_url, text, time, media, media_count, media_truncated. Its own counts are not given by Facebook in the sharing post. Null on other posts.
listingA buy-and-sell listing's own fields: id, title, price (as Facebook shows it, such as "Contact seller" or "$40"), location, is_sold, and marketplace_url for a Marketplace item posted to the group. Null on an ordinary post: a price is never read from a post's text.
top_commentThe first top comment Facebook shows with the post: id, text, time, likes, replies, author_name, author_id, author_url, url. Null when the post shows none.
top_commentsWith maxCommentsPerPost 1-10: up to that many comments of the post from one more call, each as in top_comment (the leader's topComments); else the top comment alone.
comments_statusserved (the comments call answered), none (the post has no comment: no call), refused (Facebook refused the call; the row is delivered without them), not_asked (maxCommentsPerPost is 0, or the post came already).
group_idThe group's numeric id, on every row.
group_nameThe group's name (the leader's groupTitle), on every row.
group_urlThe group's link (the leader's facebookUrl).
group_membersOn a post row: the group's exact member count, from its About page once a run (includeGroupInfo). Null with includeGroupInfo off, or on a row read from a post link.
group_privacyOn a post row: public (the posts this Actor reads come from public groups).
privacyOn a group or input row: public or private, from the group's About page.
privacy_textThe About page's own line: "Anyone can see who's in the group and what they post." or "Only members can see …".
visibilityvisible (anyone can find the group) or hidden, from the About page.
membersThe group's exact member count ("373,967 total members" on its About page); it moves by the hour.
members_textThe About page's member line as served.
new_members_textThe About page's new-members line as Facebook serves it to a logged-out reader ("No new members in the last week" on every group read in testing, a busy one too: the count is for members).
posts_last_dayPosts in the group in the last day, as the About page counts them.
posts_last_monthPosts in the group in the last month, as the About page counts them.
created_atWhen the group was created, UTC.
descriptionThe group's own description.
rulesThe titles of the group's rules, in order.
rules_countHow many rules the group lists.
cover_urlThe group's cover photo (a Facebook link that expires).
viewOn a group's input row: the order read (CHRONOLOGICAL new posts, RECENT_ACTIVITY, TOP_POSTS, CHRONOLOGICAL_LISTINGS).
verdictOn an input row: COMPLETE (read to the list's own end, read twice), CAPPED (resultsLimit, maxGroupsPerQuery, maxItems or your charge limit reached; next_cursor says where), DATE_LIMIT (the date window's older end reached) or PARTIAL (stopped early: note says why).
rows_deliveredOn an input row: the post rows (or, for a search, the group rows) it delivered and charged.
posts_readOn a group's input row: the posts read, the ones the filters left out included.
newest_timeOn a group's input row: the newest post time read.
oldest_timeOn a group's input row: the oldest post time read; give it as onlyPostsOlderThan to read on from there.
callsOn a group's input row: the feed calls the walk made (3 posts a call).
next_cursorOn a group's input row: Facebook's cursor where the walk stopped (CAPPED, PARTIAL), null at the list's end.
search_queryOn a found group's row and its search's input row: the words searched.
search_engineThe web index that listed the groups (yahoo, else bing): Facebook's own group search is closed to a logged-out reader.
search_rankOn a found group's row: its place in the web index's order (1 = first).
noteWhy an input row has the status or the verdict it has.
scraped_atWhen this row was read (UTC).
story_idFacebook's own id of the post's feed story (the leader's id, the UzpfS… form).
author_picture_urlThe author's profile picture as Facebook shows it beside the post (a Facebook link that expires).
author_is_verifiedTrue when Facebook shows the verified badge beside the author's name on the post, false when it shows none; null when the post has no name line to read.
locationsThe places the group's admins set on its About page (such as "Barcelona, Spain"); empty when they set none.
topicsThe topics the group's admins set on its About page (such as "Mathematics"); empty when they set none.

Example record:

{
"record_type": "post",
"status": "ok",
"input": "https://www.facebook.com/groups/306490195164828/",
"post_id": "1150908894056283",
"url": "https://www.facebook.com/groups/306490195164828/posts/1150908894056283/",
"feedback_id": "ZmVlZGJhY2s6cGZiaWQwMk45eTNFV21xU0g4clFrd0xWYWtqUlYxVXN5d3lIelpBbUdXckVEeFBtVDVNQzNuN3VWaVBvQWhFRWt0ZkNvN1hs",
"post_type": "text",
"is_video": false,
"is_share": false,
"time": "2026-11-05T09:17:21Z",
"timestamp": 1793870241,
"video_publish_time": null,
"text": "Should we cut back hydrangeas please",
"text_length": 36,
"hashtags": [],
"mentions": [],
"links_in_text": [],
"author_id": "2292218444903000",
"author_name": "Anonymous participant",
"author_url": null,
"author_type": "anonymous",
"reactions": 1,
"likes": 1,
"reaction_types_count": 1,
"reactions_like": 1,
"reactions_love": 0,
"reactions_care": 0,
"reactions_haha": 0,
"reactions_wow": 0,
"reactions_sad": 0,
"reactions_angry": 0,
"comments": 16,
"shares": 0,
"video_views": null,
"video_plays": null,
"video_post_views": null,
"media": [],
"media_count": 0,
"media_truncated": false,
"video_captions_url": null,
"link": null,
"event": null,
"shared_post": null,
"listing": null,
"top_comment": {
"id": "1150949240718915",
"text": "(a member's comment)",
"time": "2026-11-05T09:18:55Z",
"likes": 8,
"replies": 0,
"author_name": "A member",
"author_id": "100000000000001",
"author_url": null,
"url": "https://www.facebook.com/groups/306490195164828/posts/1150908894056283/?comment_id=1150949240718915"
},
"top_comments": [
{
"id": "1150949240718915",
"text": "(a member's comment)",
"time": "2026-11-05T09:18:55Z",
"likes": 8,
"replies": 0,
"author_name": "A member",
"author_id": "100000000000001",
"author_url": null,
"url": "https://www.facebook.com/groups/306490195164828/posts/1150908894056283/?comment_id=1150949240718915"
}
],
"comments_status": "not_asked",
"group_id": "306490195164828",
"group_name": "Gardening tips and tricks",
"group_url": "https://www.facebook.com/groups/306490195164828/",
"group_members": 99470,
"group_privacy": "public",
"privacy": null,
"privacy_text": null,
"visibility": null,
"members": null,
"members_text": null,
"new_members_text": null,
"posts_last_day": null,
"posts_last_month": null,
"created_at": null,
"description": null,
"rules": null,
"rules_count": null,
"cover_url": null,
"view": null,
"verdict": null,
"rows_delivered": null,
"posts_read": null,
"newest_time": null,
"oldest_time": null,
"calls": null,
"next_cursor": null,
"search_query": null,
"search_engine": null,
"search_rank": null,
"note": null,
"scraped_at": "2026-11-05T09:44:40Z",
"story_id": "UzpfSTIyOTIyMTg0NDQ5MDMwMDA6Vks6MTE1MDkwODg5NDA1NjI4Mw==",
"author_picture_url": null,
"author_is_verified": false,
"locations": null,
"topics": null
}

Pricing

Pay per post delivered and per group a search finds, plus one run start; no platform usage and no proxy traffic is billed to you.

eventunitFreeStarterScaleBusiness
Post (post)per 1,000$5.00$4.00$3.30$2.50
Group found (group)per 1,000$3.00$2.55$2.10$1.50
Run start (start)per run$0.0045$0.0045$0.0045$0.0045

A post is $5.00 per 1,000 on the Free plan ($0.005 a post) and $4.00 on Starter. Everything the row carries is inside that price: the text, the time, the reactions by type, the comment and share counts, the author's public name and link, the media, the shared post, the post's link and feedback id, the group's member count and privacy, and the comments of maxCommentsPerPost. The date window is free: no add-on for onlyPostsNewerThan / onlyPostsOlderThan, and none for textContains or authorContains. A group a keyword search finds and delivers is $3.00 per 1,000 on the Free plan and $2.55 on Starter; a group you give as a link is never charged. Each run that delivers a charged row also pays the run start, $0.0045 once; a run that delivers none pays nothing at all. So one post costs $0.0095 on the Free plan and $0.0085 on Starter; a group's newest 20 posts $0.1045 and $0.0845; 1,000 posts $5.0045 and $4.0045; a search that finds 10 groups $0.0345 and $0.03. Free: every input's summary row, a private, missing or empty group, a value that is not a group link, a post given twice, a group a search found outside your privacy or member range, a post a filter or the date window leaves out, and an input left unread at maxItems, your charge limit or the time limit. A run that stops early (a timeout, an abort) is charged for the rows it delivered. maxItems counts the charged rows across inputs. Before the first request the log names the price of a post (and of a group found) at your plan, the run start and the most the run can cost when resultsLimit, maxGroupsPerQuery or maxItems bounds it (under your charge limit). With resultsLimit 0 and no maxItems there is no such bound: Facebook gives no count of a group's posts ahead, and a list's end is far apart from group to group (a small group of our tests ended at 62 posts, read to its end twice; a group of 710 members still had posts after 300, back six months), so set resultsLimit, maxItems or a charge limit for a deep walk. Enterprise plans have their own rates — the Actor's Pricing tab shows the price for your plan.

Usage patterns

  • Deep walks, the orders and the date window — resultsLimit (20 unless you set it) counts the posts delivered from each group after the filters; 0 reads every post the group's feed serves, 3 posts a call, to Facebook's own end. viewOption takes the group's own orders: CHRONOLOGICAL (new posts, the default), RECENT_ACTIVITY, TOP_POSTS, CHRONOLOGICAL_LISTINGS (buy-and-sell listings). onlyPostsNewerThan / onlyPostsOlderThan take a date (2026-09-01), a time (2026-09-01T12:00:00Z) or a span back from now (7 days, 2 months). maxItems caps the whole run's charged rows. A group's walk is one page after another (Facebook's cursor), so several groups in one run read at the same time and one deep group takes about 2 seconds a call.
  • Filters and comments — textContains keeps the posts whose text or shared text holds any of your words, authorContains the posts whose author's name holds any of yours (both case-insensitive); a filtered walk reads 20 calls, then 7 a delivered post, and its row says how many matched. A post a filter leaves out is free. maxCommentsPerPost 1-10 adds up to that many comments a post from one more call (free); every comment and reply is our Facebook Comments Scraper's job, by the row's feedback_id.
  • What a row is — record_type = post: one post, charged. record_type = group: one group a search found, charged. record_type = target: one free row per input with its status, verdict, rows_delivered, posts_read, the newest and oldest post time read, the group's facts and a note saying why it stopped. The photo and video links are Facebook's own and stop working after some days: download what you keep.

Input configuration

fieldtypedefaultwhat it does
startUrlsarray[]One per line. A public group's link (https://www.facebook.com/groups/selftaughtprogrammers/, /groups/
resultsLimitinteger20The posts to deliver from each group, after the filters below. 0 = every post the group's feed serves, to the list's own end (3 posts a call: a deep walk takes time). Empty = 20.
viewOptionCHRONOLOGICAL / RECENT_ACTIVITY / TOP_POSTS / CHRONOLOGICAL_LISTINGS"CHRONOLOGICAL"The group's own sort: new posts first (the default), recent activity, top posts, or buy-and-sell listings (newest first). The date window stops a new-posts walk at its older end; in the other orders it is a filter.
onlyPostsNewerThanstringOnly posts from this time on: a date (2026-10-01, 00:00 UTC), a time (2026-10-01T12:00:00Z) or a span back from now (7 days, 2 months). Free (no add-on price): a new-posts walk stops at the first older post.
onlyPostsOlderThanstringOnly posts up to this time: a date (2026-10-01 = up to 00:00 UTC that day), a time or a span back from now. The newer posts are read on the way (at most 100 calls) and not delivered.
textContainsarray[]Deliver only the posts whose text (or the shared post's text) contains any of these words, case-insensitive. A filtered walk reads 20 calls, then 7 a delivered post, and its group row says how many matched.
authorContainsarray[]Deliver only the posts whose author's public name contains any of these words, case-insensitive.
includeGroupInfobooleantrueRead each group's About page once (one call a group): the exact member count, the privacy, posts in the last day and month, the created date, the description and the rules, on the group's row, and the member count and privacy on every post row. Off: a numeric id's posts are read with no page call (a group name still needs it).
maxCommentsPerPostinteger00 = the first top comment the post itself carries (no extra call); 1-10 = up to that many comments, from one more call a post that has comments (slower). Free either way. Every comment and reply of a post: give its feedback_id to our Facebook Comments Scraper.
searchQueriesarray[]One search a line (maths formulas). Each gives up to maxGroupsPerQuery public groups in a web index's order (Facebook's own group search is closed to a logged-out reader), one row a group with its exact member count and privacy. The groups' posts are not read: put the links you want in Facebook groups above.
maxGroupsPerQueryinteger10The most groups to deliver for each search (1-50).
groupPrivacyany / public / private"any"Deliver only the found groups of this privacy.
minMembersinteger0Deliver only the found groups with at least this many members (the exact count); 0 = no bound.
maxMembersinteger0Deliver only the found groups with at most this many members; 0 = no bound.
maxItemsinteger0The most charged rows of the whole run (posts and found groups), across all inputs; 0 = no cap beyond your charge limit.
proxyUrlstringYour own proxy (scheme://user:pass@host:port) for every call instead of ours. Leave empty: the Actor brings its own connections at no cost to you.

Errors

A run does not fail because of your input. When an input cannot be used — a date that is not a date, an id in the wrong form, two settings that contradict each other — the run ends Succeeded, charges nothing, and says what to change:

  • the status message starts with INPUT REJECTED;
  • the dataset holds one row, {"error": true, "code": "…", "message": "…"}, and no results;
  • the key-value store record ERROR holds the same object.

From code, check error on the first row before reading results.

A private group, a group that does not exist, an empty group, or a value that is not a Facebook group link is not an error: it gets one free row with its status and the reason (with the group's member count and privacy when Facebook shows them), and the run goes on with the others. A run that ends Failed is a fault on our side, never your input; it charges nothing, and we are alerted.

FAQ

Which status and verdict is which?

A post or group row is ok. An input row: ok with a verdict (COMPLETE: read to Facebook's own end, read twice; CAPPED: resultsLimit, maxGroupsPerQuery, maxItems or your charge limit reached; DATE_LIMIT: the window's older end reached; PARTIAL: stopped early, the note says why), or free: private (a private group: only members see its posts), not_found (no such group or post, on two connections), invalid_input (not a group link, an empty value), duplicate (the same group as another value of the run), failed (Facebook refused every connection tried; run it again later), not_read (maxItems, your charge limit or the time limit came first).

Can it read private groups?

No. A private group's posts are for its members, and this Actor uses no account. A private group gets a free row with its name, member count and privacy, so you know what it is.

Does it read every post a group has?

It reads what the group's logged-out feed serves, in the order you choose, to Facebook's own end flag. A group whose feed is mostly one admin's posts (welcome posts, for one) is served as Facebook lists it. An album gives its first 5 photos with the album's real count beside them.

Why does the group search not find my group by its exact name?

Facebook's own group search is closed to a logged-out reader, so the search reads a web index (site:facebook.com/groups <words>) and gives the groups in its order. A large group the index does not list for your words can be missing; give its link in startUrls instead.

Does it need a Facebook account, cookies or an API key?

No. Everything is read from Facebook's public, logged-out pages: no login, no cookie, no token of yours. The connections are included in the price.

Integration

JavaScript

import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: 'YOUR_TOKEN' });
const run = await client.actor('hyperbach/facebook-groups-scraper').call({"startUrls": ["https://www.facebook.com/groups/selftaughtprogrammers/"], "resultsLimit": 20});
const { items } = await client.dataset(run.defaultDatasetId).listItems();

Python

from apify_client import ApifyClient
client = ApifyClient('YOUR_TOKEN')
run = client.actor('hyperbach/facebook-groups-scraper').call(run_input={'startUrls': ['https://www.facebook.com/groups/selftaughtprogrammers/'], 'resultsLimit': 20})
items = client.dataset(run['defaultDatasetId']).list_items().items

CLI

$apify call hyperbach/facebook-groups-scraper --input '{"startUrls": ["https://www.facebook.com/groups/selftaughtprogrammers/"], "resultsLimit": 20}'

REST

curl -X POST "https://api.apify.com/v2/acts/hyperbach~facebook-groups-scraper/run-sync-get-dataset-items?token=YOUR_TOKEN" \
-H 'Content-Type: application/json' -d '{"startUrls": ["https://www.facebook.com/groups/selftaughtprogrammers/"], "resultsLimit": 20}'

AI agents and MCP

Apify's MCP server offers this Actor as a tool to Claude, Cursor, VS Code and any other MCP client. Connect https://mcp.apify.com?tools=hyperbach/facebook-groups-scraper and ask, for example: "Get the newest 50 posts of the public Facebook group selftaughtprogrammers with their reactions, comments and authors". The agent fills the input from the table above and reads the rows from the run's dataset. A field under the name another Actor gives it is read as this Actor's own: urls, url, links, groupUrls as startUrls; search, searchQuery, queries, query as searchQueries; maxPosts, postsLimit, maxPostsPerGroup, postsPerGroup as resultsLimit; sortBy, sort, sorting, sortingSetting as viewOption (and more).

n8n, Make and Zapier

The Apify node in n8n, the Apify app in Make and the Apify integration in Zapier run this Actor on a schedule or from a trigger and read its dataset. A webhook on the run's end (Integrations on the Actor page) sends the rows on to your own endpoint. Nothing to install on our side.

Support

Disagree with a charge? Write to apify@hyperbach.com with the run ID. We will ask Apify to compensate you, and the charge comes back to your Apify account as platform credit.

Did it do the job? A short review on the Store, at any rating, helps the next buyer choose.

This page is generated from the Actor's schemas and a live sample — it cannot describe a field the Actor does not have.