# B2B Agency Leads — Clutch, GoodFirms, DesignRush + Emails (`shrid5/agency-leads-scraper`) Actor

Scrape agencies from Clutch, GoodFirms, and DesignRush: name, website, rating, rates, and location, with optional email extraction from agency websites.

- **URL**: https://apify.com/shrid5/agency-leads-scraper.md
- **Developed by:** [Shrithan](https://apify.com/shrid5) (community)
- **Categories:** Lead generation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.00 / 1,000 agency listings

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

## B2B Agency Leads Scraper — Clutch, GoodFirms & DesignRush + Emails

Unofficial. Not affiliated with, endorsed by, or sponsored by Clutch, GoodFirms, or DesignRush.

Scrape B2B agencies from Clutch, GoodFirms, and DesignRush in a single run: name, website, rating, reviews, hourly rates, team size, and location, with optional email extraction from each agency's public site. Built for outbound sales, agency partnership teams, and lead-gen agencies who need directory leads they can actually contact.

### What you get

Each dataset item is one agency. Primary key is `profileUrl`.

```json
{
  "source": "clutch",
  "name": "Power Digital",
  "profileUrl": "https://clutch.co/profile/power-digital",
  "website": "https://powerdigitalmarketing.com/growthplan",
  "tagline": "Power Digital is a comprehensive advertising agency specializing in digital marketing services, including SEO, paid media, and content creation.",
  "rating": 4.8,
  "reviewCount": 66,
  "minProjectSize": "$5,000+",
  "hourlyRate": "$100 - $149 / hr",
  "employees": "250 - 999",
  "servicesFocus": ["Advertising", "Social Media Marketing", "Pay Per Click", "Search Engine Optimization"],
  "location": "San Diego, CA",
  "country": "US",
  "emails": []
}
```

### How to use

1. Open this Actor in Apify Console. **Category is required** (for example `digital marketing` or `seo`). Pick one or more sources: Clutch, GoodFirms, DesignRush — default is all three.
2. Set **Max results per source** to cap cost. Leave **Extract emails** off for a cheap directory pull; turn it on when you need contact addresses from agency websites.
3. Click **Start**. Export the dataset as JSON, CSV, or Excel when the run finishes.

Worked example input (digital marketing agencies, 5 per directory, no email crawl):

```json
{
  "sources": ["clutch", "goodfirms", "designrush"],
  "category": "digital marketing",
  "maxResultsPerSource": 5,
  "includeEmails": false
}
```

Category aliases include marketing, web development, seo, mobile apps, design, and it-services. Unknown text falls back to each site's directory root. GoodFirms uses live listing paths (for example `/directory/marketing-services/top-digital-marketing-companies`) — not the stale `/companies/...` slugs.

### Pricing

| Event | Price | When you are charged |
| --- | --- | --- |
| Actor start (`apify-actor-start`) | $0.00005 | Once per run (automatic; first 5 seconds of compute are covered) |
| Listing (`listing`) | $0.002 | Each unique agency written to the dataset |
| Email enrichment (`email-enrichment`) | $0.005 | Each agency where at least one email was found (in addition to listing) |

Scraping 5,000 agencies without emails costs **$10.00 + $0.00005 start fee**. If 1,000 of those also return an email, add **$5.00**.

You are not charged `email-enrichment` when `emails` is `[]`. You are not charged `listing` on a zero-result run (beyond the start fee).

### Monitor mode / scheduling

Turn on **Monitor mode (new agencies only)** and create a daily or weekly schedule in Apify Console (Actor → Schedules).

- The actor stores a cursor (profile URLs already seen) in a named key-value store, keyed by your sources + category + location, so two schedules with different filters do not overwrite each other.
- **First monitor run** (no cursor yet): emits every matching agency up to your cap, then saves the cursor (capped at 50,000 URLs).
- **Later runs**: skip profile URLs already in the cursor — a feed of newly listed agencies.
- Changing `maxResultsPerSource` or `includeEmails` does not reset the cursor.

### Integrations

- **API:** Call actor `shrid5/agency-leads-scraper` (or `https://apify.com/shrid5/agency-leads-scraper`) with the Apify REST API or JS/Python client. Pass the same JSON input as the Console form.
- **MCP:** Apify Actors are callable from MCP/AI-agent clients, so an assistant can search agency directories and return structured leads.
- **Webhooks:** Fire a webhook on run success to notify Slack, a CRM, or your own endpoint.
- **Make / Zapier / n8n:** Use the official Apify apps to send new agency rows into Google Sheets, HubSpot, Salesforce, or email.

### FAQ

**How do I get a list of SEO agencies?**
Set Category to `seo` and leave Sources on all three (or Clutch only). Raise Max results per source if you need more than the default 200.

**Do you extract emails from Clutch/GoodFirms/DesignRush profiles?**
No. Emails come from the agency's own public website (homepage, `/contact`, `/contact-us`, `/about`) when **Extract emails** is on. Directory pages rarely publish emails. Empty `emails: []` is a valid result and is not billed as enrichment.

**Why is GoodFirms missing some categories?**
GoodFirms listing URLs change. This actor maps marketing to the live `/directory/marketing-services/top-digital-marketing-companies` path (the old `/companies/digital-marketing` slug is a 404). Unknown categories use the GoodFirms directory root.

**Can I filter by city or country?**
Yes — set Location (for example `Austin` or `US`). Directories do not share one geo URL scheme, so the actor post-filters listing location/country fields.

**Is scraping these directories legal?**
This actor reads public listing pages only. You are responsible for how you use the leads (CAN-SPAM, GDPR/CCPA, and each directory's terms). We do not log in, bypass paywalls, or invent contact data.

**How does billing work if I hit my spending cap?**
The actor charges `listing` after each agency is written (and `email-enrichment` only when an email was found). If your max-total-charge limit is reached it logs `Charge limit reached, stopping gracefully`, saves the monitor cursor, and stops without throwing.

### Support

Maintained by [Shrithan](https://apify.com/shrid5). Open an issue on this Actor or email shrithanofficial@gmail.com.

# Actor input Schema

## `sources` (type: `array`):

Directories to scrape. Allowed values: clutch, goodfirms, designrush. Leave as all three to search every directory in one run.

## `category` (type: `string`):

What kind of agency you want (for example digital marketing, seo, web development, mobile apps, design, or it-services). Each directory maps this to the closest live listing URL. Unknown values fall back to that site's directory root.

## `location` (type: `string`):

Optional city or country filter. Applied as a post-filter on listing location/country fields (directories do not all share a common geo URL param).

## `maxResultsPerSource` (type: `integer`):

Stop after this many agencies from each directory. Use a small number to estimate cost, then raise it for a full pull.

## `includeEmails` (type: `boolean`):

When enabled, fetch each agency homepage plus /contact, /contact-us, and /about, then extract emails. Agencies with no email still emit a listing (emails: \[]). You are charged email-enrichment only when at least one email is found.

## `monitorMode` (type: `boolean`):

When enabled, skip profile URLs already seen in previous runs for the same sources + category + location. Schedule this actor daily or weekly in Apify Console. The first monitor run returns the full matching set, then saves a cursor of up to 50,000 profile URLs.

## Actor input object example

```json
{
  "sources": [
    "clutch",
    "goodfirms",
    "designrush"
  ],
  "category": "digital marketing",
  "maxResultsPerSource": 5,
  "includeEmails": false,
  "monitorMode": false
}
```

# Actor output Schema

## `dataset` (type: `string`):

Dataset of agency listings (name, website, rating, location, emails).

# 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 = {
    "sources": [
        "clutch",
        "goodfirms",
        "designrush"
    ],
    "category": "digital marketing",
    "maxResultsPerSource": 5
};

// Run the Actor and wait for it to finish
const run = await client.actor("shrid5/agency-leads-scraper").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 = {
    "sources": [
        "clutch",
        "goodfirms",
        "designrush",
    ],
    "category": "digital marketing",
    "maxResultsPerSource": 5,
}

# Run the Actor and wait for it to finish
run = client.actor("shrid5/agency-leads-scraper").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 '{
  "sources": [
    "clutch",
    "goodfirms",
    "designrush"
  ],
  "category": "digital marketing",
  "maxResultsPerSource": 5
}' |
apify call shrid5/agency-leads-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,shrid5/agency-leads-scraper"
        }
    }
}

```

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/2sQrIqvstgOdEQ4fU/builds/64vUcGQ5yeYGCtWes/openapi.json
