# Find Backlinks (`winningsolutions/backlink-list-exporter`) Actor

Export a flat backlink list for one domain, subdomain, or page. Page beyond 1,000 rows, filter by rank and date, and write one dataset row per backlink.

- **URL**: https://apify.com/winningsolutions/backlink-list-exporter.md
- **Developed by:** [Winning Solutions](https://apify.com/winningsolutions) (community)
- **Categories:** SEO tools, Developer tools
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

$3.30 / 1,000 results

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

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

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
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.
Actors are written with capital "A".

## 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.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## Find Backlinks - Flat List Export, Up to 10,000 Rows Per Run

A **research Actor** that returns a flat backlink list for one target at scale. Enter one **target domain, subdomain, or page URL** and configure mode, limits, filters, and sort order. The Actor turns that input into structured results automatically.

It returns **structured JSON** with **url\_from**, **url\_to**, **domain\_from**, **anchor**, **dofollow**, **rank**, **domain\_from\_rank**, **first\_seen**, **last\_seen**, and **source\_total\_count**.

Designed for **SEO teams, agencies, and developers** who need a programmatic backlink list with one dataset row per backlink. Every run writes diagnosis rows when nothing matches, so empty results stay visible. Official backlink index data. Structured JSON. No silent empty datasets.

> ## Paging beyond the 1,000-row limit
>
> **Need more than 1,000 backlinks? Set maxResults above 1000.**
>
> The source returns up to 1,000 items per page. This Actor pages with offset until your row limit or page cap is reached. After the run, count dataset rows: values above 1,000 mean paging worked. **One flat row per backlink, not a nested array.**

### Use Cases

- Export a **flat backlink list** for one domain or page URL
- Pull **more than 1,000 backlinks** when the source reports a higher total
- Filter by **dofollow**, **lost status**, **domain rank**, or **first seen** dates
- Switch **list mode** to one row per domain or per anchor
- Feed **SEO audits** and link research pipelines with structured JSON

### Index

- [Release Notes](#release-notes)
- [Features](#features)
- [Use Cases](#use-cases)
- [Pricing](#pricing)
- [Input](#input)
- [Input Example](#input-example-target-domain)
- [API and MCP usage](#api-and-mcp-usage)
- [Output Structure](#output-structure)
- [Output Example](#output-example)

### Release Notes

#### v0.0 - Initial public release

- **Flat backlink list:** One dataset row per backlink for a single target
- **Paging over 1,000:** maxResults up to 10,000 with automatic offset paging
- **Filters and modes:** Dofollow, lost, rank, first seen, and three list modes

### Features

📊 **One row per backlink:** The dataset is the list. No nested `backlinks[]` array in a single row.

📄 **Paging beyond 1,000:** maxResults above 1000 triggers multiple source pages until your cap or maxPages is reached.

🔍 **Server-side filters:** Dofollow, lost, domain rank, and first seen filters run at the source, not after download.

📅 **First seen window:** Optional from and to dates in YYYY-MM-DD format filter backlinks by first seen date.

🎯 **Three list modes:** as\_is, one\_per\_domain, and one\_per\_anchor use the same per-row pricing.

📈 **Source total on every row:** Each backlink row carries source\_total\_count so you see how much remains beyond your cap.

🛑 **Independent page limit:** maxPages stops fetching even when maxResults is not reached, with a clear log line and diagnosis row.

⚡ **Diagnosis rows:** Empty runs, caps, page limits, and input errors write explicit dataset rows instead of failing silently.

### Pricing

#### Regular pricing

| Cost item | Rate |
| --------- | ---- |
| Result-Event (1 backlink row) | $0.0033 |
| Per 1,000 backlink rows | $3.30 |
| Apify platform compute (RAM/time) | Billed by Apify platform pricing |

> **Cost per backlink row: ~$0.0033** - Default run with 100 rows costs about $0.33 with no extra events.

You pay only for backlink rows written with resultCharged true. Diagnosis rows are free.

#### Free plan limit

Runs from Apify free plan accounts are limited to 100 backlink rows per run.
The run finishes normally at that point and keeps every result already written.

#### Cost Examples

Based on the regular prices above.

**Scenario A: Default run (100 backlink rows)**

- 100 backlink rows: $0.33
- **Total: ~$0.33**

**Scenario B: One full source page (1,000 backlink rows)**

- 1,000 backlink rows: $3.30
- **Total: ~$3.30**

**Scenario C: Hero paging (2,000 backlink rows)**

- 2,000 backlink rows: $6.60
- **Total: ~$6.60**

### Input

The Actor accepts the following input parameters (see the **Input** tab in the Apify Console for the full, interactive schema):

| Parameter | Type | Required | Default | Description |
| --------- | ---- | -------- | ------- | ----------- |
| `target` | string | yes | none | Domain, subdomain, or page URL. One target per run. Domain or subdomain: no scheme and no leading www. Page: absolute URL with http:// or https://. No lists, no spaces, no IP literal. |
| `mode` | string | no | `as_is` | How the source cuts the list. as\_is keeps every backlink. one\_per\_domain and one\_per\_anchor return one representative backlink per group. |
| `maxResults` | integer | no | `100` | Max backlink rows to write. Values above 1000 are allowed. Hard cap is 10000. Free plan users stop at 100 rows. This is not a full dump. |
| `maxPages` | integer | no | `50` | Max source pages to fetch. Stops the search even if fewer rows were written. Independent of maxResults. Default 50. Values outside 1-50 are rejected, not clamped. |
| `dofollowOnly` | boolean | no | `false` | If true, keep only dofollow backlinks. Default keeps nofollow rows. |
| `excludeLost` | boolean | no | `false` | If true, drop lost backlinks. Default keeps lost rows. |
| `minDomainRank` | integer | no | none | If set, keep rows whose source domain rank is at least this value. Default applies no rank filter. Allowed range is 0-1000. Values outside that range are rejected, not clamped. |
| `firstSeenFrom` | string | no | none | If set, keep backlinks first seen on or after this date. Format is YYYY-MM-DD. Datetime values are rejected. |
| `firstSeenTo` | string | no | none | If set, keep backlinks first seen on or before this date. Format is YYYY-MM-DD. Datetime values are rejected. |
| `orderBy` | string | no | `rank,desc` | Sort rule sent to the source. One rule only. Default is rank descending. |

#### Input Example (target domain)

```json
{
  "target": "example.com",
  "maxResults": 100
}
```

### API and MCP usage

Runs write **one dataset row per backlink**. Diagnosis rows use the same dataset when a run ends without backlink rows or hits a cap.
Fetch rows from the default dataset after the run succeeds (or use the synchronous endpoint below).

**REST (sync, returns dataset items):** replace `YOUR_USERNAME`, `YOUR_API_TOKEN`, and use the same JSON body as in [Input Example](#input-example-target-domain).

```bash
curl "https://api.apify.com/v2/acts/YOUR_USERNAME~backlink-list-exporter/run-sync-get-dataset-items?token=YOUR_API_TOKEN" \
  -X POST \
  -H "Content-Type: application/json" \
  -d '{"target":"example.com","maxResults":100}'
```

**JavaScript (`apify-client`):**

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

const client = new ApifyClient({ token: process.env.APIFY_TOKEN });
const input = {
  target: 'example.com',
  maxResults: 100,
};
const run = await client.actor('YOUR_USERNAME~backlink-list-exporter').call(input);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items);
```

**Apify MCP server (AI agents):** configure your MCP client with URL `https://mcp.apify.com?tools=YOUR_USERNAME~backlink-list-exporter` (you can combine multiple tools per [Apify MCP docs](https://docs.apify.com/platform/integrations/mcp)). Pass the API token via your client (for example an `Authorization: Bearer ...` header), not inside the Actor input JSON.

### Output Structure

The Actor returns structured data for each backlink row. The table below lists the main fields. Optional dataset views in the Apify Console may show a subset.

| Field | Type | Description | Example Value |
| ----- | ---- | ----------- | ------------- |
| `type` | string | Item type from the source | `backlink` |
| `domain_from` | string | Referring domain | `referrer.example` |
| `url_from` | string | Referring page URL | `https://referrer.example/page` |
| `url_to` | string | Target page URL | `https://example.com/` |
| `anchor` | string | Link anchor text, may be empty | `example` |
| `dofollow` | boolean | Whether the link is dofollow | `true` |
| `rank` | number | Backlink rank score | `142` |
| `domain_from_rank` | number | Rank of the referring domain | `210` |
| `first_seen` | string | First time the backlink was seen | `2020-01-15 12:00:00 +00:00` |
| `last_seen` | string | Last time the backlink was seen | `2026-08-01 08:00:00 +00:00` |
| `is_lost` | boolean | Whether the backlink is lost | `false` |
| `target` | string | Normalized input target | `example.com` |
| `mode` | string | Input list mode | `as_is` |
| `source_total_count` | number | Total backlinks the source reports for the target | `67093202` |
| `_metadata.resultCharged` | boolean | Whether this row was charged | `true` |
| `_metadata.error` | string | null | Present on failure or empty diagnostic rows | *(varies)* |
| `_metadata.errorContext` | string | null | Extra error context when `error` is set | *(varies)* |

#### Output Example

```json
{
  "type": "backlink",
  "domain_from": "referrer.example",
  "url_from": "https://referrer.example/page",
  "url_to": "https://example.com/",
  "anchor": "example",
  "dofollow": true,
  "rank": 142,
  "domain_from_rank": 210,
  "first_seen": "2020-01-15 12:00:00 +00:00",
  "last_seen": "2026-08-01 08:00:00 +00:00",
  "is_lost": false,
  "target": "example.com",
  "mode": "as_is",
  "source_total_count": 67093202,
  "_metadata": {
    "resultCharged": true,
    "error": null,
    "errorContext": null
  }
}
```

# Actor input Schema

## `target` (type: `string`):

Domain, subdomain, or page URL. One target per run. Domain or subdomain: no scheme and no leading www. Page: absolute URL with http:// or https://. No lists, no spaces, no IP literal.

## `mode` (type: `string`):

How the source cuts the list. as\_is keeps every backlink. one\_per\_domain and one\_per\_anchor return one representative backlink per group.

## `maxResults` (type: `integer`):

Max backlink rows to write. Values above 1000 are allowed. Hard cap is 10000. Free plan users stop at 100 rows. This is not a full dump.

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

Max source pages to fetch. Stops the search even if fewer rows were written. Independent of maxResults. Default 50. Values outside 1-50 are rejected, not clamped.

## `dofollowOnly` (type: `boolean`):

If true, keep only dofollow backlinks. Default keeps nofollow rows.

## `excludeLost` (type: `boolean`):

If true, drop lost backlinks. Default keeps lost rows.

## `minDomainRank` (type: `integer`):

If set, keep rows whose source domain rank is at least this value. Default applies no rank filter. Allowed range is 0-1000. Values outside that range are rejected, not clamped.

## `firstSeenFrom` (type: `string`):

If set, keep backlinks first seen on or after this date. Format is YYYY-MM-DD. Datetime values are rejected. last\_seen and prev\_seen are not inputs.

## `firstSeenTo` (type: `string`):

If set, keep backlinks first seen on or before this date. Format is YYYY-MM-DD. Datetime values are rejected.

## `orderBy` (type: `string`):

Sort rule sent to the source. One rule only. Default is rank descending. This is not a separate "best first" mode.

## Actor input object example

```json
{
  "target": "example.com",
  "mode": "as_is",
  "maxResults": 100,
  "maxPages": 50,
  "dofollowOnly": false,
  "excludeLost": false,
  "firstSeenFrom": "2020-01-01",
  "firstSeenTo": "2026-12-31",
  "orderBy": "rank,desc"
}
```

# Actor output Schema

## `results` (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 = {
    "target": "example.com"
};

// Run the Actor and wait for it to finish
const run = await client.actor("winningsolutions/backlink-list-exporter").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 = { "target": "example.com" }

# Run the Actor and wait for it to finish
run = client.actor("winningsolutions/backlink-list-exporter").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 '{
  "target": "example.com"
}' |
apify call winningsolutions/backlink-list-exporter --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,winningsolutions/backlink-list-exporter"
        }
    }
}

```

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/ktYywjTXOjzhl6gcm/builds/ldZHYJFlaKOxUpqYg/openapi.json
