How to Scrape Facebook Comments (2026 Guide)
Need to extract Facebook comments programmatically? Whether you're building brand monitoring tools, customer support triage, social listening platforms, or research datasets, getting reliable Facebook comment data is essential.
In this guide, we'll show you the easiest way to scrape Facebook comments using the Facebook Comments API. No proxies, no Puppeteer, no Page tokens, no app review. Includes cursor-based pagination so you can walk full threads on viral Page videos.
What Data Can You Extract?
The Facebook Comments API provides comprehensive comment information:
- Comment Content - Full comment text with emoji support
- Author Information - Display name, profile URL, profile picture
- Engagement Metrics - Reaction counts and reply counts per comment
- Page-Author Detection -
isAuthorflag identifies page-owner replies - Cursor Pagination - Walk thousands of comments on long-running posts
- Multi-Format URLs -
facebook.com/watch?v=,/<page>/videos/<id>/, and/reel/<id>/
The Easy Way: Facebook Comments API
The simplest and most reliable method is using the Facebook Comments API. Here's why:
✅ No Infrastructure Needed - No proxies, browsers, or anti-bot systems
✅ No Facebook Developer Account - No Page tokens, no app review
✅ Always Up-to-Date - API automatically handles Facebook changes
✅ Cursor Pagination - Walk full threads on viral page content reliably
✅ Fast & Reliable - Get comment data with a single REST call
✅ Simple Integration - Just one API call with a Facebook URL
✅ Structured Data - Clean JSON response ready for your application
API Endpoint
https://api.socialkit.dev/facebook/comments
Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
url | string | Yes | Facebook URL (/watch?v=, /<page>/videos/<id>/, or /reel/<id>/) |
access_key | string | Yes | Your API access key |
limit | number | No | Comments per request (max 100, default 10) |
cursor | string | No | Cursor from a previous response to fetch the next page |
Example Request
GET https://api.socialkit.dev/facebook/comments?access_key=<your-access-key>&url=https://www.facebook.com/watch?v=876091671461782&limit=20
Example Response
{
"success": true,
"data": {
"url": "https://www.facebook.com/watch?v=876091671461782",
"postUrl": "https://www.facebook.com/watch?v=876091671461782",
"commentCount": null,
"comments": [
{
"id": "Y29tbWVudDoxMjY3NzU2MzkxODQwNDc5XzIwNzg1MTcyNDk1NjYxMjU=",
"name": "Kelly Mcpherson",
"profileUrl": "https://www.facebook.com/...",
"profilePicUrl": "https://scontent.fbcdn.net/...",
"text": "Why does he look like Steve from stranger things? 🤷🏻",
"likes": 24,
"replyCount": 2,
"date": "12-17-2025",
"timestamp": 1734456789,
"isAuthor": false
},
{
"id": "Y29tbWVudDoxMjY3NzU2MzkxODQwNDc5Xzg4MzQ5NDI1Nzk3NzgzMA==",
"name": "Zach Hager",
"profileUrl": "https://www.facebook.com/...",
"profilePicUrl": "https://scontent.fbcdn.net/...",
"text": "Is that the guy from Stranger Things?",
"likes": 8,
"replyCount": 0,
"date": "12-17-2025",
"timestamp": 1734456823,
"isAuthor": false
}
],
"limit": 20,
"hasMore": true,
"cursor": "MToxNzc3ODg2MTM0OgF_QDTIzMZ6Yln0..."
}
}
Note: Facebook does not expose total comment count via this endpoint, so
commentCountisnull. UsehasMoreto know when you've reached the end of the thread.
Code Examples
JavaScript / Node.js
const axios = require('axios');
async function getFacebookComments(postUrl, accessKey, options = {}) {
const params = {
access_key: accessKey,
url: postUrl,
limit: options.limit || 50,
};
if (options.cursor) params.cursor = options.cursor;
const response = await axios.get(
'https://api.socialkit.dev/facebook/comments',
{ params }
);
return response.data;
}
// Usage
const postUrl = 'https://www.facebook.com/watch?v=876091671461782';
const accessKey = 'your-access-key';
getFacebookComments(postUrl, accessKey, { limit: 50 }).then((data) => {
console.log(`Returned in this page: ${data.data.comments.length}`);
data.data.comments.forEach((c) => {
const tag = c.isAuthor ? ' [author]' : '';
console.log(`\n${c.name}${tag}: ${c.text}`);
console.log(` Reactions: ${c.likes} | Replies: ${c.replyCount}`);
});
if (data.data.hasMore) {
console.log(`\nNext cursor: ${data.data.cursor.slice(0, 60)}...`);
}
});
Python
import requests
def get_facebook_comments(post_url, access_key, limit=50, cursor=None):
endpoint = 'https://api.socialkit.dev/facebook/comments'
params = {'access_key': access_key, 'url': post_url, 'limit': limit}
if cursor: params['cursor'] = cursor
response = requests.get(endpoint, params=params)
response.raise_for_status()
return response.json()
# Usage
post_url = 'https://www.facebook.com/watch?v=876091671461782'
access_key = 'your-access-key'
data = get_facebook_comments(post_url, access_key, limit=50)
print(f"Returned: {len(data['data']['comments'])}")
for c in data['data']['comments']:
tag = ' [author]' if c['isAuthor'] else ''
print(f"\n{c['name']}{tag}: {c['text']}")
print(f" Reactions: {c['likes']:,} | Replies: {c['replyCount']}")
PHP
<?php
function getFacebookComments($postUrl, $accessKey, $limit = 50, $cursor = null) {
$params = [
'access_key' => $accessKey,
'url' => $postUrl,
'limit' => $limit,
];
if ($cursor) $params['cursor'] = $cursor;
$url = 'https://api.socialkit.dev/facebook/comments?' . http_build_query($params);
$response = file_get_contents($url);
return json_decode($response, true);
}
$data = getFacebookComments(
'https://www.facebook.com/watch?v=876091671461782',
'your-access-key',
50
);
foreach ($data['data']['comments'] as $c) {
$tag = $c['isAuthor'] ? ' [author]' : '';
echo "{$c['name']}{$tag}: {$c['text']}\n";
echo " Reactions: " . number_format($c['likes']) . " | Replies: {$c['replyCount']}\n\n";
}
cURL
curl -X GET "https://api.socialkit.dev/facebook/comments?access_key=your-access-key&url=https://www.facebook.com/watch?v=876091671461782&limit=50"
Walking the Full Thread with Cursor Pagination
Page videos with high engagement can have thousands of comments. The cursor field lets you walk the entire thread reliably:
async function getAllFacebookComments(postUrl, accessKey, maxComments = 500) {
const all = [];
let cursor = null;
while (all.length < maxComments) {
const remaining = maxComments - all.length;
const params = {
access_key: accessKey,
url: postUrl,
limit: Math.min(100, remaining),
};
if (cursor) params.cursor = cursor;
const { data } = await axios.get(
'https://api.socialkit.dev/facebook/comments',
{ params }
);
all.push(...data.data.comments);
if (!data.data.hasMore || !data.data.cursor) break;
cursor = data.data.cursor;
}
return all;
}
// Usage
const comments = await getAllFacebookComments(
'https://www.facebook.com/watch?v=876091671461782',
'your-access-key',
500
);
console.log(`Pulled ${comments.length} comments across all pages`);
def get_all_facebook_comments(post_url, access_key, max_comments=500):
all_comments = []
cursor = None
while len(all_comments) < max_comments:
remaining = max_comments - len(all_comments)
data = get_facebook_comments(
post_url, access_key,
limit=min(100, remaining),
cursor=cursor,
)
all_comments.extend(data['data']['comments'])
if not data['data']['hasMore'] or not data['data']['cursor']:
break
cursor = data['data']['cursor']
return all_comments
Use Cases
1. Brand Reputation Pulse
Score sentiment across your last 50 page videos, alert on spikes:
async function brandReputationPulse(pageVideoUrls, accessKey, openaiKey) {
const allComments = [];
for (const url of pageVideoUrls) {
const data = await getFacebookComments(url, accessKey, { limit: 50 });
allComments.push(...data.data.comments);
}
// Send to OpenAI for sentiment scoring
const response = await fetch('https://api.openai.com/v1/chat/completions', {
method: 'POST',
headers: {
Authorization: `Bearer ${openaiKey}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
model: 'gpt-4o-mini',
messages: [{
role: 'user',
content: `Score sentiment % across these comments:\n${
allComments.map((c) => `${c.name}: ${c.text}`).join('\n')
}`,
}],
response_format: { type: 'json_object' },
}),
});
return response.json();
}
2. Customer Support Triage
Classify comments and route into your support queue:
import re
SUPPORT_KEYWORDS = ['help', 'broken', 'issue', 'refund', 'cancel', "doesn't work"]
def triage_page_comments(page_video_urls, access_key):
tickets = []
for url in page_video_urls:
data = get_facebook_comments(url, access_key, limit=50)
for c in data['data']['comments']:
text_lower = c['text'].lower()
for kw in SUPPORT_KEYWORDS:
if kw in text_lower:
tickets.append({
'video_url': url,
'commenter': c['name'],
'profile': c['profileUrl'],
'comment': c['text'],
'reactions': c['likes'],
'replies': c['replyCount'],
'flagged_keyword': kw,
})
break # one tag per comment
return tickets
3. Page-Owner Reply Tracker
Surface where the brand has replied vs gone silent:
async function findUnansweredQuestions(postUrl, accessKey) {
const all = await getAllFacebookComments(postUrl, accessKey, 200);
// Group by parent (note: replyCount > 0 means it has replies)
const topLevel = all.filter((c) => !c.isAuthor && c.replyCount === 0);
const questions = topLevel.filter((c) =>
c.text.includes('?') && c.likes >= 3
);
return questions.map((c) => ({
commenter: c.name,
profileUrl: c.profileUrl,
question: c.text,
reactions: c.likes,
}));
}
4. Audience Demographic Mapping
Build a profile of who engages with your Page videos:
def map_audience(page_video_urls, access_key):
profile_set = set()
for url in page_video_urls:
data = get_facebook_comments(url, access_key, limit=100)
for c in data['data']['comments']:
if c['profileUrl']:
profile_set.add(c['profileUrl'])
return {
'unique_commenters': len(profile_set),
'profile_urls': sorted(profile_set),
}
Response Data Explained
Comment Object Fields
id- Unique comment identifier (base64-encoded global Facebook ID)name- Commenter's display nameprofileUrl- URL to the commenter's Facebook profileprofilePicUrl- Profile picture URL (signed CDN link)text- Comment text contentlikes- Total reaction count (reactions, not just thumbs-up)replyCount- Number of threaded replies under this commentdate- Comment date in MM-DD-YYYY formattimestamp- Unix timestamp (seconds)isAuthor-trueif commenter is the post author (page-owner reply)
Top-Level Fields
url- The URL you submittedpostUrl- Canonical Facebook post URLcommentCount-nullfor Facebook (usehasMoreinstead)limit- Limit applied to this responsehasMore-trueif more comments are availablecursor- Opaque token to pass back for the next page
Note: Unlike Instagram or YouTube, Facebook's pagination response doesn't include a total comment count. Use
hasMoreto know when you've walked the full thread.
Supported URL Formats
The API accepts various Facebook URL formats:
https://www.facebook.com/watch?v=<video_id>(Watch videos)https://www.facebook.com/<page-name>/videos/<video_id>/(Page videos)https://www.facebook.com/reel/<video_id>/(Facebook Reels)https://m.facebook.com/...(mobile URLs - resolved automatically)
Error Handling
Implement retry logic for production reliability:
async function getFacebookCommentsWithRetry(
postUrl, accessKey, options = {}, maxRetries = 3
) {
for (let i = 0; i < maxRetries; i++) {
try {
return await getFacebookComments(postUrl, accessKey, options);
} catch (error) {
if (i === maxRetries - 1) throw error;
await new Promise((r) => setTimeout(r, 1000 * Math.pow(2, i)));
}
}
}
Common error responses:
| Status | Meaning | What to Do |
|---|---|---|
400 | Missing url parameter | Check the request includes a valid Facebook URL |
403 | Out of credits | Top up at /pricing |
404 | Post not found or comments disabled | Post may be private, deleted, or the page restricted comments |
408 | Timeout | Retry with exponential backoff |
500 | Server error | Retry; if persistent, check status |
Pricing & Credits
The Facebook Comments API uses 1 credit per 50 comments returned (minimum 1 credit per request).
Monthly plans:
- Free: 20 credits to start
- Starter ($19/mo): 4,000 credits, good for ~200,000 comments
- Standard ($29/mo): 12,000 credits, good for ~600,000 comments (most popular)
- Ultimate ($95/mo): 50,000 credits, bulk research scale
Pay-as-you-go (one-time, never expires):
- Starter Pack ($14): 1,000 credits
- Growth Pack ($49): 20,000 credits
- Scale Pack ($249): 150,000 credits
Free Tools
Test the API quality without writing code first:
- Free Facebook Comment Viewer - View and export comments from any post, watch video, or reel as CSV, JSON, or TXT
- Free Facebook Comments Analyzer - AI sentiment analysis with themes and key takeaways
Conclusion
The Facebook Comments API gives you full access to Page video, watch, post, and reel comments without proxies, Puppeteer, scraping infrastructure, or Facebook's Graph API approval process. Cursor pagination lets you walk the full thread on viral content, page-author flags help you isolate brand replies, and a clean JSON response drops straight into any brand-monitoring or support-triage pipeline.
Start with the free Facebook Comment Viewer to see what the response looks like, then grab 20 free API credits to wire it into your stack.
Related Resources: