# B2B Leads Finder: Companies Hiring Now, With Contact Details (`glitchbound/b2b-leads-finder`) Actor

Companies that are hiring right now, each with the contact details their own website publishes. A prospect list with a buying signal attached.

- **URL**: https://apify.com/glitchbound/b2b-leads-finder.md
- **Developed by:** [Daniel Meshulam](https://apify.com/glitchbound) (community)
- **Categories:** Lead generation, Jobs, Automation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.50 / 1,000 company leads

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/platform/actors/running/actors-in-store#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 Leads Finder: Companies Hiring Now, With Contact Details

**23,717 companies that are actively hiring**, ranked by how hard, each with the
company contact details their own website publishes. **7,551 of them are reachable.**

Most contact scrapers start from a list you already have: paste URLs, get
emails. The hard part of prospecting was never extracting an address from a
page you already chose. **It is choosing the page.**

This starts from a buyer intent signal instead: who is hiring, and how hard.

```
company                open  30d   7d   net   pace      reach
BAYADA Home Health     2585 1456  449  +1456  surging   facebook.com/bayadahomehealthcare
Bjak                   1414 1174  361  +1164  surging   support@bjak.my
Anduril Industries     2170  612   48   +586  surging   contact@anduril.com
Ouihelp                 685  588  201   +588  surging   contact@ouihelp.fr
```

A company that opened 40 roles this month is expanding, and expansion is when
budget appears. A company opening its **first** roles in sales, security or
finance has just changed strategy, and that is the strongest single signal in
the dataset.

### What you get back

One row per company:

| field | notes |
|---|---|
| `company`, `website` | the employer and its own domain |
| `contactEmails` | role addresses it publishes: `info@`, `sales@`, `careers@` |
| `contactPhones` | numbers from a `tel:` link, which is the publisher saying it is one |
| `socialProfiles` | its own LinkedIn, X, Facebook, Instagram, YouTube |
| `openRoles`, `opened7`, `opened30`, `opened90` | the hiring signal |
| `closed30`, `net30` | roles that disappeared, and the net change |
| `hiringLabel` | surging (top 1%), growing (top 10%), steady, slow, quiet |
| `newDepartments30` | functions entered in the last 30 days |
| `departments`, `locations` | what and where they are hiring |
| `contactsHarvested` | whether we have crawled this company's site at all |

### Filters

- **`minOpenedLast30`**, **`minOpenedLast7`** the signal, at two windows
- **`growingOnly`** / **`shrinkingOnly`** net change positive or negative
- **`withContactOnly`** (on by default) only companies we can reach
- **`withEmailOnly`** stricter: a published role address must be present
- **`enteringNewDepartments`** only companies moving into a new function
- **`hiringLabels`**, **`minOpenRoles`**, **`company`**, **`department`**,
  **`location`**, **`platforms`**
- **`includeStaffingAgencies`** off by default; they post for others and
  otherwise dominate every ranking

Filtered companies are never returned and never charged.

### Honest limits

These matter more than the feature list.

**Reach is 32%, and every company in the index has been crawled.** This is the
steady-state number, not a work in progress: the remainder is companies whose
own site publishes no contact route at all, or that refuse an ordinary HTTP
request, not companies we have not got to. Measured across the whole index: a domain resolves for 40.9%, a social profile is found for 29.3%, a published role address for 14.2%, a phone for 10.2%. 0.6% asked us not to crawl them and were
not crawled.

**This does not change what a search returns.** `withContactOnly` is on by
default, so you only ever see companies we can actually reach; the percentage
above describes the index behind it, not the rows you get.

**`contactsHarvested` tells you which kind of empty you are looking at.** A
company we have not reached and a company that publishes nothing must not read
the same, because they send you to two different places.

**No personal addresses, ever.** Only role addresses a company publishes as a
way to be contacted. Nothing is guessed: no `first.last@` patterns, no
permutation, no verification service, no cookies and no logins. A named
individual's address is not collected even when it is sitting in plain sight,
because it was published so a person could do their job, not so a stranger
could buy a list.

**Closures need history.** `closed30` and `net30` are absent, not zero, until
this index has watched a company for long enough to know. "Closed nothing" and
"we do not know yet" must never look the same.

**The signal is hiring, not intent.** A company expanding its support team is
not necessarily buying your product. This narrows a market to the accounts
where something is changing; qualifying them is still your job.

### What kind of data this is

If you buy sales data, the categories you already know map onto this cleanly,
so here is where it sits and where it does not.

**Buyer intent data, of one specific kind.** Intent data providers mostly sell
web-visit and content-consumption signals bought from third-party networks.
This is not that. Hiring is a first-party intent signal a company publishes
about itself: it posts the role because it wants applicants, and a company
staffing a function is a company spending on it. Narrower than a full intent
feed, and observable rather than inferred.

**Sales trigger events.** The classic trigger is "started hiring for X", and
`newDepartments30` is exactly that: a company entering a function it was not
hiring into before. `shrinkingOnly` is the mirror trigger, a company whose
closures outrun its openings, which is a churn warning if they are your
customer.

**A company email finder, restricted to company addresses.** Filter by
`company` name and you get that employer's published contact routes. It finds
the company's own role addresses, `info@`, `sales@`, `careers@`, from the
company's own website. **It does not find a named person's email**, not a CEO's
and not an employee's, and it never guesses one from a name pattern. If that is
what you need, this is the wrong tool and no amount of filtering will turn it
into the right one.

**A lead list builder, not a lead enricher.** You do not hand it a list; it
produces one from the hiring signal. If you already have accounts and want
fields added to them, that is a different job.

### Where the data comes from

Every company's own applicant tracking system (Greenhouse, Ashby, Workable,
Recruitee, Personio, Rippling, BambooHR, Breezy, Teamtailor),
read through the API each employer publishes so aggregators can syndicate it,
and every company's own website for the contact details. Rebuilt nightly. No
account of yours is ever involved.

# Actor input Schema

## `minOpenedLast30` (type: `integer`):

The buying signal. A company that opened 20+ roles this month is expanding, and expansion is when budget appears. Leave empty for all.

## `minOpenedLast7` (type: `integer`):

Tighter and fresher than the 30-day figure. Use it when you want this week's movers rather than this month's.

## `growingOnly` (type: `boolean`):

Opened more roles than they closed over 30 days. Needs closure history, so companies we cannot judge yet are excluded rather than assumed.

## `shrinkingOnly` (type: `boolean`):

Closed more than they opened. A churn warning, and the signal no one-off scrape can compute: you cannot see a job close if you were not there when it opened.

## `withContactOnly` (type: `boolean`):

Only companies whose own website publishes a role address, a phone number in a tel: link, or their own social profiles.

## `withEmailOnly` (type: `boolean`):

Stricter than the above: a role address such as info@ or sales@ must be present. Never a named individual's address, and never guessed.

## `hiringLabels` (type: `array`):

surging (top 1%), growing (top 10%), steady, slow, quiet.

## `minOpenRoles` (type: `integer`):

Company size proxy. Filters out one-role boards.

## `company` (type: `array`):

Match specific accounts by name.

## `department` (type: `array`):

Match the departments a company is hiring into: Sales, Engineering, Finance. A company opening its first roles in a function has just changed strategy.

## `location` (type: `array`):

Match where the company is hiring.

## `enteringNewDepartments` (type: `boolean`):

Companies hiring into a department they were not in before. The strongest strategy-change signal in the dataset.

## `includeStaffingAgencies` (type: `boolean`):

Off by default. Agencies post on behalf of others and otherwise dominate every ranking.

## `platforms` (type: `array`):

Restrict to certain applicant tracking systems, one per line, e.g. greenhouse or workday. Leave empty to search every platform in the index.

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

Ceiling on rows returned and charged. 1,000 default, 10,000 max.

## Actor input object example

```json
{
  "growingOnly": false,
  "shrinkingOnly": false,
  "withContactOnly": true,
  "withEmailOnly": false,
  "enteringNewDepartments": false,
  "includeStaffingAgencies": false,
  "maxResults": 200
}
```

# 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 = {
    "maxResults": 200
};

// Run the Actor and wait for it to finish
const run = await client.actor("glitchbound/b2b-leads-finder").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 = { "maxResults": 200 }

# Run the Actor and wait for it to finish
run = client.actor("glitchbound/b2b-leads-finder").call(run_input=run_input)

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

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

```

## CLI example

```bash
echo '{
  "maxResults": 200
}' |
apify call glitchbound/b2b-leads-finder --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "command": "npx",
            "args": [
                "mcp-remote",
                "https://mcp.apify.com/?tools=glitchbound/b2b-leads-finder",
                "--header",
                "Authorization: Bearer <YOUR_API_TOKEN>"
            ]
        }
    }
}

```

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/XBucORNAKFpdjZQNX/builds/aNaavRWVP53Ze6MAF/openapi.json
