# Facebook Ads Library Scraper & Creative Intelligence (`herazur/facebook-ads-library-scraper-creatives`) Actor

Enter a competitor domain to find active Meta ads, copy, CTAs, images, videos and landing URLs. Rank long-running ads, repeated creatives and likely winner candidates.

- **URL**: https://apify.com/herazur/facebook-ads-library-scraper-creatives.md
- **Developed by:** [Furkan Toluç](https://apify.com/herazur) (community)
- **Categories:** Social media, Marketing, Lead generation
- **Security:** Limited permissions
- **Stats:** 1 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.40 / 1,000 ad analyzeds

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## Facebook Ads Library Scraper & Creative Intelligence

Enter a competitor domain to find active Meta (Facebook and Instagram) ads with copy, headlines, CTAs, images, videos, landing URLs, start dates and ad age. Rank long-running ads, repeated creatives and likely winner candidates in a ready-to-use intelligence report highlighting **longest-running ads**, **repeated creatives**, **likely winner candidates**, **offers**, **hooks** and **creative angles**.

Built for agencies, ecommerce teams and marketers who need a one-time creative research export. No Meta login, cookies or AI key required.

### Quick start

```json
{"domain":"allbirds.com","maxAds":100,"country":"ALL"}
```

The Store input form is prefilled with a small trial (`allbirds.com`, 20 ads, one advertiser page, a $0.10 source budget). Raise `maxAds` and `maxSourceChargeUsd` for larger exports.

1. Enter a competitor domain.
2. Run the Actor.
3. Export the default dataset as JSON, CSV or Excel.
4. Open **Creative intelligence report** in the Output tab for the ranked summary.

### What you get

Each dataset row is one unique, explicitly active ad from a Facebook page linked on the competitor homepage, or an ad with a verified landing URL on the domain when homepage discovery is unavailable:

| Field | Meaning |
| --- | --- |
| `adId`, `pageId`, `pageName` | Ad and advertiser identity |
| `adCopy`, `headline`, `cta` | Public ad text; variants are preserved in separate arrays |
| `creative`, `imageUrls`, `videoUrls` | Original image and video links when available |
| `creativeVariants` | Individual carousel card text, CTA, media and destination |
| `landingUrl`, `landingUrls` | Public destination URLs; Facebook link wrappers are decoded |
| `startDate`, `adAgeDays` | Public start date and elapsed calendar duration |
| `adLibraryUrl` | Link back to the original Meta Ad Library record |
| `intelligence` | Duration, repetition, winner-candidate, offer, hook and angle evidence |
| `missingFields` | Fields not provided by the source |

The `INTELLIGENCE` key-value record contains the longest-running ranking, repeated creative groups, likely winner shortlist, source run IDs, filtering counts, coverage limitations and a link to the companion tracker. Unknown fields remain null or empty; they are never invented.

### How discovery works

First, the Actor reads the competitor's HTTPS homepage and finds its Facebook page links. It scrapes active ads from those pages, including ads that open Facebook collections rather than the brand website. Each row includes `attributionMethod: HOMEPAGE_FACEBOOK_LINK` and the homepage and Facebook page URLs as evidence.

If the homepage is unavailable or has no usable Facebook link, the Actor searches Meta Ad Library for the domain text, verifies destination hostnames, then expands active ads from discovered advertiser pages. In this fallback mode it filters all results by destination domain, using `attributionMethod: LANDING_DOMAIN`. For example, `allbirds.com.kw` is not a match for `allbirds.com`. All results are deduplicated by ad ID.

A link is attribution evidence, **not legal proof of brand ownership**. Homepage links can identify regional or partner pages; fallback domain searches can include affiliates advertising your website. In fallback mode, ads without an identifiable matching destination, including unresolved shortened links, are excluded.

Set `maxAds` to `0` to request all accessible ads on discovered pages. Discovery caps, source budgets, Meta search behavior and availability still apply. The report always sets `completeCoverageGuaranteed: false`; it never claims a complete census. An empty result means no verified matches in this search, not proof of no advertising.

### Intelligence methodology

- **Longest Running Ads:** active ads sorted by public start-date age. This is elapsed age, not verified uninterrupted delivery time.
- **Repeated Creatives:** same advertiser and same exact set of media URL paths, ignoring expiring query parameters. Distinct ad IDs are counted once. Missing media never creates a repetition group. This is not perceptual image similarity.
- **Likely Winners:** candidates must be at least `longRunningDays` old and reuse media across at least two returned ads. Score: `min(70, round(ageDays / threshold * 35)) + min(30, (repetitions - 1) * 10)`. Reasons are included. Score is a heuristic, not a probability.
- **Offer:** explicit English phrases such as discounts, free shipping, trials, BOGO and limited-time offers, with exact evidence.
- **Hook:** the opening sentence or line of ad copy, up to 280 characters.
- **Creative Angle:** English text cues for offer, social proof, convenience, product benefit, sustainability or problem/solution. Unrecognized angles remain empty.

No spend, conversion, ROAS or profitability data is inferred. No OCR, video transcription or visual content analysis is performed. Rankings and repetition counts describe the returned sample.

### Input options

| Input | Default | Notes |
| --- | --- | --- |
| `domain` | Required | Public website domain or URL |
| `country` | `ALL` | Uppercase two-letter country code or ALL |
| `maxAds` | 100 | 0–10,000; 0 requests all accessible results |
| `longRunningDays` | 30 | 7–365 days |
| `discoveryLimit` | 200 | 30–1,000 keyword search results |
| `maxPages` | 5 | 1–20 homepage-linked or discovered advertiser pages |
| `maxSourceChargeUsd` | 2 | $0.10–$50 combined child scraping budget |

### Pricing

On the Apify Free plan: **$2 per 1,000 analyzed ads** ($0.002 for each output ad), plus a $0.00005 Actor start event at the default memory setting. Paid Apify plans get lower per-ad prices: $0.0018 (Bronze), $0.0016 (Silver), and $0.0014 (Gold and higher). No analysis charge for an empty dataset or failed collection.

**Source scraping charges are additional.** This Actor calls [Facebook Ads Library Scraper by curious_coder](https://apify.com/curious_coder/facebook-ads-library-scraper) using your Apify execution context. Its current price is shown on its own pricing page. Discovery records, nonmatching ads and repeated reads can incur source charges even when excluded from the final dataset. `maxSourceChargeUsd` caps the aggregate child-run budget; the parent run's maximum charge controls this Actor's fees separately. Failed source runs may still incur source fees.

For example, 100 analyzed results cost $0.20 in analysis fees plus the small start fee and whatever the source runs actually consumed. The report records source run IDs and accounted source charges for auditing. Because final billing aggregates can settle after a child finishes, budget accounting uses the run's event prices as a conservative floor.

### Track changes after scraping

Use [Facebook Ads Library Competitor Tracker](https://apify.com/herazur/facebook-ads-library-competitor-tracker) to track new ads, stopped ads and creative changes over time. This scraper does not maintain a monitoring baseline. The intelligence report includes suggested Facebook page URLs for the tracker; select a specific country supported by that Actor.

### Reliability and limitations

Source errors fail the run rather than masquerading as an empty successful scrape. Source scraping can change when Meta changes its interfaces. Public dates and media are returned as provided; CDN URLs may expire. Dynamic template placeholders are excluded when real card copy is available. Missing dates are never treated as zero-day ads. Use the Issues tab with your run ID and input domain if a run fails.

This independent tool is not affiliated with Meta. It processes public ad-library content and does not access private advertiser accounts.

# Actor input Schema

## `domain` (type: `string`):

Website domain, for example allbirds.com. Finds Facebook page links on its homepage and scrapes their active ads. Falls back to verified landing-domain search if no page link is available.

## `country` (type: `string`):

ALL or an uppercase ISO country code, such as US, GB or TR.

## `maxAds` (type: `integer`):

Maximum analyzed ads. Set 0 to request all accessible results from discovered pages, subject to source budget, discovery and platform limits. Complete coverage is never guaranteed.

## `longRunningDays` (type: `integer`):

Minimum public ad age for the long-running signal. Likely winner candidates additionally require repeated media.

## `discoveryLimit` (type: `integer`):

Number of keyword search results used to discover advertisers linking to the domain. The source may overshoot by about 30 records.

## `maxPages` (type: `integer`):

Expand active ads from up to this many domain-linked advertiser pages. A domain link does not prove advertiser ownership.

## `maxSourceChargeUsd` (type: `number`):

Combined budget for child scraper runs, separate from this Actor's analysis charge. Source charges include discovered ads later filtered out. Default $2; source failures prevent a complete report.

## Actor input object example

```json
{
  "domain": "allbirds.com",
  "country": "ALL",
  "maxAds": 20,
  "longRunningDays": 30,
  "discoveryLimit": 30,
  "maxPages": 1,
  "maxSourceChargeUsd": 0.1
}
```

# Actor output Schema

## `ads` (type: `string`):

No description

## `intelligence` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "domain": "allbirds.com",
    "maxAds": 20,
    "discoveryLimit": 30,
    "maxPages": 1,
    "maxSourceChargeUsd": 0.1
};

// Run the Actor and wait for it to finish
const run = await client.actor("herazur/facebook-ads-library-scraper-creatives").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "domain": "allbirds.com",
    "maxAds": 20,
    "discoveryLimit": 30,
    "maxPages": 1,
    "maxSourceChargeUsd": 0.1,
}

# Run the Actor and wait for it to finish
run = client.actor("herazur/facebook-ads-library-scraper-creatives").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "domain": "allbirds.com",
  "maxAds": 20,
  "discoveryLimit": 30,
  "maxPages": 1,
  "maxSourceChargeUsd": 0.1
}' |
apify call herazur/facebook-ads-library-scraper-creatives --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,herazur/facebook-ads-library-scraper-creatives"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/vIPyUQhl03QpvXW9D/builds/8CsIyVcMbqy7Y7SGz/openapi.json
