# LinkedIn Leads Finder: Apollo, ZoomInfo & Lusha Alternative (`pnda/linkedin-scraper`) Actor

LinkedIn leads finder: Apollo, ZoomInfo and Lusha alternative with fresh leads and live-verified work emails, no cookies or login. Search people and companies by job title, city and keywords, scrape LinkedIn profiles, companies, jobs and posts. Sales Navigator alternative. $3.50/1,000 profiles.

- **URL**: https://apify.com/pnda/linkedin-scraper.md
- **Developed by:** [PNDA](https://apify.com/pnda) (community)
- **Categories:** Lead generation, Social media, Jobs
- **Features:** Limited permissions
- **Stats:** 67 total users, 41 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: 5.00 out of 5 stars

## Pricing

from $3.50 / 1,000 profiles

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

## LinkedIn Leads Scraper: Apollo, ZoomInfo & Lusha Alternative

**Fresh B2B leads straight from LinkedIn, with live-verified work emails. A LinkedIn scraper with no cookies and no login.** Search LinkedIn people and companies by keyword, job title and location, scrape full **profiles**, **company data**, **jobs** and **posts** from URLs, and get **verified work emails**. One actor, pay per result.

- 🔒 **No cookies, no login, no LinkedIn account.** Nothing touches your account, so it can never be restricted or banned.
- 🔎 **LinkedIn search without Sales Navigator** (`mode: "search"`): find LinkedIn profiles like *"CEO, marketing agency, Paris"* or companies like *"SaaS, London"*. A **Sales Navigator alternative** for lead generation, built on Google x-ray search of public LinkedIn pages.
- 🏢➡️👤 **Company → decision makers**: find companies, then the CEO / head of sales / recruiter at each one, in the same run.
- 📧 **Verified work email** (`findEmail`): name + company → professional email, checked live over SMTP. **$9 / 1,000 emails found**, charged only when verified.
- 🧩 **A LinkedIn API alternative**: call it over HTTP from the Apify API, n8n, Make, Zapier, Clay or your own code. No LinkedIn developer app, no partner approval.
- 💸 **Pay only for rows you receive.** Invalid URLs, dead pages and empty searches are **never charged**.
- 🆓 **Works with a free Apify account too**: every mode at the same prices, from your monthly Apify credit (shared daily capacity for free accounts).
- 📦 Export to **JSON, CSV, Excel, HTML, XML** or stream the dataset straight into your pipeline.

***

### 🆚 Apollo, ZoomInfo & Lusha alternative: fresh leads, not an old database

Lead databases are built once and resold for months: people change jobs, emails start bouncing, and you pay for contacts that no longer exist. This actor works the other way round: **every lead is found on LinkedIn at the moment you run it**.

| | Lead databases (Apollo, ZoomInfo, Lusha...) | This actor |
|---|---|---|
| Where the data comes from | A database refreshed from time to time | Live public LinkedIn pages, at run time |
| Job title and company | Can be months old | What the profile shows today |
| Work email | Often guessed or stale | Checked live on the mail server, charged only when valid |
| Bounced addresses | Stay in the list | Addresses reported as bounced are removed automatically |
| Pricing | Seats, monthly plans, credit packs | Pay per result, no subscription |
| Search | Their filters, their index | Job title, company, city and keywords, like a LinkedIn search |

**Typical use:** describe your ideal leads (*"head of sales, SaaS, London"*), get the matching LinkedIn profiles, their full profile and a verified work email, then export to your CRM, Clay, n8n, Make or Zapier.

***

### 🚀 From a LinkedIn search to a verified email, in one run

No URL list needed. Describe who you are looking for, and the actor chains three steps:

1. **🔎 Search**: Google x-ray search of public LinkedIn pages finds the matching people (or companies). No LinkedIn account, no cookies.
2. **👤 Profile**: each person found is scraped for the full profile (experience, education, current company...).
3. **📧 Verified email**: the work email is built from the name and company, then verified live over SMTP.

Example: CEOs of agencies in Paris, with full profiles and verified emails:

```json
{
  "mode": "search",
  "searchType": "people",
  "role": "CEO",
  "location": "Paris",
  "keywords": "agence",
  "maxResults": 20,
  "scrapeResults": true,
  "findEmail": true
}
```

One row per person (illustrative values, trimmed):

```json
{
  "resultType": "people",
  "linkedinUrl": "https://www.linkedin.com/in/jane-doe",
  "name": "Jane Doe",
  "position": "CEO",
  "company": "Acme Agency",
  "query": "CEO agence Paris site:linkedin.com/in",
  "rank": 1,
  "details": {
    "name": "Jane Doe",
    "position": "CEO at Acme Agency",
    "city": "Paris, Île-de-France, France",
    "current_company": { "name": "Acme Agency", "title": "CEO" },
    "experience": [{ "title": "CEO", "company": "Acme Agency", "start_date": "..." }]
  },
  "email": "jane.doe@acme-agency.fr",
  "email_status": "found",
  "email_confidence": "verified",
  "email_pattern": "first.last",
  "email_domain": "acme-agency.fr",
  "email_domain_source": "guessed-from-company"
}
```

Each step is billed only for what it returns: **$3.50 / 1,000 people found** (launch price), $3.50 / 1,000 profiles scraped, $9 / 1,000 **verified** emails. For 20 CEOs with 8 verified emails: about $0.14. Launch pricing: search results are billed at the profile price until the dedicated search price ($4.90 / 1,000) applies on November 10. Already have LinkedIn URLs? Pick **"Scrape LinkedIn URLs"** instead.

***

### 💡 Who is it for?

- **Sales & SDR teams** building lead lists from a LinkedIn search (title + industry + city) without Sales Navigator, then enriching them (job title, company, seniority) before outreach.
- **Recruiters** pulling full candidate profiles (experience, education) in bulk.
- **RevOps / CRM owners** refreshing job titles and employers every month.
- **Market researchers & investors** collecting LinkedIn company data (size, industry, HQ, followers, headcount on LinkedIn).
- **Job-market analysts** tracking open roles of target companies as hiring signals.
- **Social & content teams** measuring reactions and comments on posts.
- **Data & AI teams** feeding LinkedIn data into scoring models, RAG pipelines or agents.

***

### ⚙️ How it works

Two modes, chosen with the first field of the form, **"What do you want to do?"**:

- **🔎 Search LinkedIn (no URL needed)** (`mode: "search"`, selected when you open the form): give a job title, a location and keywords (for example *CEO / Paris / agence*), get LinkedIn profile or company URLs with name, position, company and location. Optionally scrape each result and find its verified email. Launch price: $3.50 / 1,000 results (billed as the `profile` event) until November 10, then $4.90 / 1,000.
- **Scrape LinkedIn URLs** (`mode: "urls"`, the default over the API when `mode` is omitted): pick a content type (`Profile`, `Company`, `Job` or `Post`), paste LinkedIn URLs, get one full row per URL.

#### Scrape URLs

URLs that don't match the selected mode are skipped (and listed in the log) before anything happens. URLs that LinkedIn can't serve are saved in the key-value store record `FAILED_URLS` and are **not charged**.

| Mode | Accepted URLs | What you get |
|---|---|---|
| **Profile** | `linkedin.com/in/<handle>` | Name, headline, location, followers, connections, about, current company, full experience, education, awards, recent activity & posts, similar profiles |
| **Company** | `linkedin.com/company/<slug>` | Name, industry, company size, headquarters, website, followers, employees on LinkedIn, description, specialties, locations |
| **Job** | `linkedin.com/jobs/view/<id>` | Title, company, location, seniority, employment type, job function, industries, number of applicants, posted date, full description |
| **Post** | `linkedin.com/posts/...` or `linkedin.com/feed/update/...` | Author, post text (plain + HTML), date, likes, comments, top comments, hashtags, tagged people & companies, images, videos, documents |

Country subdomains (`fr.linkedin.com`, `uk.linkedin.com`...) and query strings are accepted.

***

### 📥 Input

| Field | Type | Required | Description |
|---|---|---|---|
| `type` | string | ✅ | `Profile` (default), `Company`, `Job` or `Post` |
| `urls` | array of strings | ✅ | LinkedIn URLs matching the selected type |
| `findEmail` | boolean | | Profile mode only, default `false`. Also finds the person's verified work email (see below) |

#### Example inputs

```json
{
  "type": "Profile",
  "urls": [
    "https://www.linkedin.com/in/satyanadella/",
    "https://www.linkedin.com/in/jeffweiner08/"
  ]
}
```

Profiles **with verified work email**:

```json
{
  "type": "Profile",
  "findEmail": true,
  "urls": ["https://www.linkedin.com/in/satyanadella/"]
}
```

```json
{
  "type": "Company",
  "urls": [
    "https://www.linkedin.com/company/microsoft/",
    "https://www.linkedin.com/company/bereal/"
  ]
}
```

```json
{ "type": "Job", "urls": ["https://www.linkedin.com/jobs/view/4440458716/"] }
```

```json
{ "type": "Post", "urls": ["https://www.linkedin.com/posts/reidhoffman_give-people-a-reason-to-want-the-ai-future-activity-7508645307132600321-dOsB"] }
```

***

### 🔎 Search LinkedIn without cookies (`mode: "search"`)

Find LinkedIn profiles and companies **without a LinkedIn account, without cookies and without Sales Navigator**. In the form, pick **"🔎 Search LinkedIn (no URL needed)"**: the search fields come right below it.

The pipeline has three steps, each billed only for what it returns:

1. **Search** (always): a Google x-ray search of public LinkedIn pages (`site:linkedin.com/in` or `site:linkedin.com/company`) finds the leads: LinkedIn URL, name, position, company, location.
2. **Scrape** (`scrapeResults`, optional): each lead's full profile or company page, same record as URL mode.
3. **Email** (`findEmail`, optional, people): the built-in email finder guesses the work email from the name and company, then verifies it live over SMTP. Only verified emails are billed.

> Pricing: launch price **$3.50 / 1,000 search results** (billed as the `profile` event) until **November 10**; from then on search results have their own `search-result` event at $4.90 / 1,000.

| Field | Description |
|---|---|
| `searchType` | `people` (profiles, default) or `company` |
| `keywords` | Industry, skills, any words: `marketing agency`, `saas`, `shopify` |
| `role` | Job title: `CEO`, `head of sales`, `recruiter` |
| `location` | City, region or country: `Paris`, `London`, `Texas` |
| `maxResults` | Max leads (default 20, min 5). Google pages hold ~10 results: multiples of 10 work best |
| `findPeopleAtCompanies` | Company search: also find people with the `role` at each company found |
| `peoplePerCompany` | 5 to 10 profiles per company (default 10) |
| `scrapeResults` | Also scrape the full profile / company page of each lead (billed like URL mode) |
| `findEmail` | Also find the verified work email of each person found |
| `country`, `language` | Google country (`us`, `fr`, `gb`...) and language (`en`, `fr`...) |

Example: CEOs of agencies in Paris, with verified emails:

```json
{ "mode": "search", "searchType": "people", "role": "CEO", "keywords": "agency", "location": "Paris", "maxResults": 50, "findEmail": true }
```

Example: marketing agencies in Lyon, then their CEO:

```json
{ "mode": "search", "searchType": "company", "keywords": "marketing agency", "location": "Lyon", "maxResults": 20, "findPeopleAtCompanies": true, "role": "CEO" }
```

Output row (real result, trimmed):

```json
{
  "resultType": "people",
  "linkedinUrl": "https://www.linkedin.com/in/valeriebodocco",
  "name": "Valérie Bodocco",
  "position": "CEO",
  "company": "L'Agence de Paris",
  "location": null,
  "title": "Valérie Bodocco - CEO - L'Agence de Paris",
  "snippet": "En immobilier, je dirige depuis 2010 le Groupe L'Agence...",
  "query": "CEO agency Paris site:linkedin.com/in",
  "rank": 1
}
```

People found through `findPeopleAtCompanies` also carry `sourceCompanyName`, `sourceCompanyUrl` and `companyMatch` (`true` when the result mentions the company; `false` rows are looser Google matches such as former employees or namesakes, and come last).

**Empty search? It is broadened for you.** When a search finds no lead, it is retried automatically, first **without the keywords**, then **without the location** (and without the keywords when a job title remains). Rows from a broadened search carry `searchBroadened` (e.g. `"without keywords \"SaaS\""`) and the run status says what was removed. If even that finds nothing, you get one free `no-results` row: *"0 results: try broader keywords, a larger city or another job title"*. Never charged.

Good to know: search covers what Google indexes of public LinkedIn pages (very broad, but not 100 % of LinkedIn), and `name` / `position` / `company` are parsed from the Google title and snippet. Turn on `scrapeResults` when you need the full, structured profile.

***

### 📤 Output examples (trimmed)

**Profile**

```json
{
  "name": "Satya Nadella",
  "first_name": "Satya",
  "last_name": "Nadella",
  "position": "Chairman and CEO at Microsoft",
  "city": "Redmond, Washington, United States",
  "country_code": "US",
  "followers": 12183622,
  "connections": 500,
  "current_company": { "name": "Microsoft", "company_id": "microsoft", "title": "Chairman and CEO" },
  "about": "As chairman and CEO of Microsoft, I define my mission...",
  "experience": [{ "title": "Chairman and CEO", "company": "Microsoft", "start_date": "..." }],
  "education": [{ "title": "The University of Chicago Booth School of Business" }],
  "url": "https://www.linkedin.com/in/satyanadella"
}
```

With `findEmail: true`, each profile row gets these extra fields:

```json
{
  "email": "jane.doe@acme.com",
  "email_status": "found",
  "email_confidence": "verified",
  "email_pattern": "first.last",
  "email_domain": "acme.com",
  "email_domain_source": "guessed-from-company"
}
```

**Company**

```json
{
  "name": "Microsoft",
  "industries": "Software Development",
  "company_size": "10,001+ employees",
  "headquarters": "Redmond, Washington",
  "website": "https://news.microsoft.com/",
  "followers": 29163922,
  "employees_in_linkedin": 231769,
  "url": "https://www.linkedin.com/company/microsoft"
}
```

**Job**

```json
{
  "job_title": "Data Engineer Expérimenté F/H",
  "company_name": "EY",
  "job_location": "Paris, Île-de-France, France",
  "job_seniority_level": "Mid-Senior level",
  "job_employment_type": "Full-time",
  "job_function": "Information Technology",
  "job_num_applicants": 98,
  "job_posted_date": "2026-09-23T08:00:26.424Z",
  "job_summary": "Chez EY, nous sommes « All in » pour façonner votre avenir...",
  "url": "https://www.linkedin.com/jobs/view/4440458716/"
}
```

**Post**

```json
{
  "user_id": "reidhoffman",
  "date_posted": "2026-09-23T21:55:45.104Z",
  "post_type": "post",
  "num_likes": 492,
  "num_comments": 151,
  "post_text": "If people can't point to something in their lives that has become easier, more affordable...",
  "url": "https://www.linkedin.com/posts/reidhoffman_give-people-a-reason-to-want-the-ai-future-activity-7508645307132600321-dOsB"
}
```

Every row also contains the original `input` and a `timestamp`. Field names are stable, so you can map them once in your CRM or spreadsheet.

***

### 📧 Find verified work emails (`findEmail`)

Turn a list of LinkedIn profile URLs into a list of **verified professional emails**, in the same run.

1. The actor takes the person's **first and last name** and **current company** from the profile.
2. The company domain comes from the profile when it is there; otherwise it is deduced from the company name (only domains that actually receive email are kept).
3. The usual corporate patterns (`first.last`, `first`, `flast`, `firstlast`...) are tested one by one with a **live SMTP check**, stopping at the first verified address.

| `email_status` | Meaning | Charged? |
|---|---|---|
| `found` | Mailbox verified (`email_confidence: "verified"`) | ✅ `email-found` |
| `catch-all` | The domain accepts every address: `email` is the most likely pattern, **unverified** (`email_confidence: "catch-all"`) | ❌ free |
| `not-found` | No tested pattern exists | ❌ |
| `unknown` | The mail server gave no clear answer | ❌ |
| `no-mx` / `no-company` | No mail domain for the current company | ❌ |

The profile itself is always delivered and billed as a normal `profile`, whatever the email result.

***

### 💰 Pricing (pay per result)

**Store discounts:** on Apify Silver, Gold, Platinum and Diamond plans, some events cost up to 20 % less. The Pricing tab of the Store page shows the exact price for each plan.

You pay a fixed price per LinkedIn record actually returned. No start fee, no monthly rental, no charge for failed URLs.

| Event | What triggers it | Price |
|---|---|---|
| `profile` | 1 profile returned | $3.50 / 1,000 |
| `company` | 1 company page returned | $6.49 / 1,000 |
| `job` | 1 job listing returned | $5.90 / 1,000 |
| `post` | 1 post returned | $5.90 / 1,000 |
| `search-result` | 1 LinkedIn profile or company found by a search (`mode: "search"`) | $4.90 / 1,000 |
| `email-found` | 1 **verified** work email found (`findEmail`) | $9.00 / 1,000 |

| Example run | Records | Approx. cost |
|---|---|---|
| Quick test | 10 profiles | ~$0.035 |
| Lead list | 1,000 profiles | ~$3.50 |
| Account list | 1,000 companies | ~$6.49 |
| Lead list + emails | 1,000 profiles, `findEmail` on, 400 verified emails | ~$3.50 + $3.60 = ~$7.10 |
| LinkedIn search | 1,000 people found by keyword + title + city | ~$4.90 |
| Search + emails | 1,000 people found, `findEmail` on, 350 verified emails | ~$4.90 + $3.15 = ~$8.05 |

**Works with a free Apify account too.** Free-plan accounts can use every feature at the same per-result prices, paid from their monthly Apify credit. Limit: free accounts share a daily capacity; once it is used up, the remaining inputs are skipped with one `free-plan-limit` row (not charged). Retry the next day, or switch to a paid Apify plan to run without this limit.

Set **Maximum cost per run** in the run options to cap your spend: duplicate URLs are removed and the actor only scrapes as many URLs as your limit can pay for; the rest are skipped and listed in the log. With `findEmail`, each URL reserves the price of a profile **and** an email. In search mode, a Google page is only requested when your limit still covers at least 5 more results.

***

### 🔌 Use it as a LinkedIn API

Run it synchronously and get the rows in one HTTP call:

```bash
curl -X POST "https://api.apify.com/v2/acts/pnda~linkedin-scraper/run-sync-get-dataset-items?token=<APIFY_TOKEN>" \
  -H "Content-Type: application/json" \
  -d '{"type":"Company","urls":["https://www.linkedin.com/company/microsoft/"]}'
```

Or use the Apify client for JavaScript/Python, the n8n / Make / Zapier integrations, webhooks, or Apify Schedules for recurring refreshes.

***

### 🚀 Why this actor

- ✅ **Search + scrape + email in one actor**: find LinkedIn profiles, scrape profiles, company data, jobs and posts, get verified emails. One integration instead of five.
- ✅ **No cookies, no login**: zero risk for your LinkedIn account.
- ✅ **Bulk by URL**: hundreds of URLs per run, one clean row per URL.
- ✅ **Rich data**: full career history, company headcount, applicants count, post engagement.
- ✅ **Fair billing**: invalid and dead URLs are never charged.

***

### ❓ FAQ

**Do I need a LinkedIn account, cookies or a proxy?** No.

**How fresh is the data?** Records are collected when you run the actor, typically within seconds to a few minutes per batch. A profile or company page already collected in the last 30 days may be served from our result cache: faster, same price, same record.

**What if a URL fails?** It is not charged. The error (e.g. `dead_page`) is stored in the key-value store record `FAILED_URLS`.

**Does it return emails?** Yes, for profiles, if you turn on `findEmail`. The email is built from the name and current company and verified over SMTP; you pay $9 / 1,000 only for verified emails. Catch-all guesses are returned for free, clearly flagged.

**Can I use it on the free Apify plan?** Yes. It works with a free Apify account too, at the same prices, paid from your monthly Apify credit. Free accounts share a daily capacity: when it is reached, the inputs left get a `free-plan-limit` row and are not charged. Paid Apify plans have no such limit ([pricing](https://apify.com/pricing)).

**Can I search LinkedIn by keyword without cookies?** Yes: `mode: "search"` finds LinkedIn profiles and companies by keyword, job title and location through Google, with no LinkedIn login, no cookies and no Sales Navigator subscription. You pay $4.90 / 1,000 results found; empty searches are free.

**Is it a Sales Navigator alternative?** For prospect lists, yes: search by title + industry + city, get profile URLs, names, positions and companies, then verified emails. It does not send connection requests or messages.

**Is it an Apollo, ZoomInfo or Lusha alternative?** For LinkedIn leads, yes. Apollo, ZoomInfo and Lusha sell access to a contact database built in advance; this actor reads public LinkedIn pages when you run it, so job titles and companies are current, and each work email is verified live before you pay for it. No seats, no monthly plan: you pay per lead.

**Is it legal?** It only collects publicly available data. You are responsible for using it in compliance with the privacy laws of your jurisdiction. Do not use personal data without a legitimate purpose.

***

### Related actors

- [Email Finder](https://apify.com/pnda/email-finder): Already have names and company domains? Find work emails without running a LinkedIn search.
- [Email Verifier](https://apify.com/pnda/email-verifier): Verify a whole email list before your outreach, $0.95 per 1,000.
- [Email Extractor](https://apify.com/pnda/email-extractor): Have company websites? Extract the emails, phones and social links they publish.
- [Crunchbase API](https://apify.com/pnda/crunchbase-scraper): Targeting startups? Find funded companies and their investors, then their people here.
- [PitchBook Scraper](https://apify.com/pnda/pitchbook-scraper): Need private company data (total raised, latest deal, investors) for your accounts.

***

### ▶️ Start now

Search LinkedIn or paste your URLs, click **Run**, export your dataset. LinkedIn data and leads on tap: no cookies, no login.

# Actor input Schema

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

"Search LinkedIn": no URL needed. Give a job title, a location and keywords; the actor finds matching LinkedIn profiles or companies through Google (no login, no cookies, no LinkedIn account), then can scrape each one and find its verified work email. "Scrape LinkedIn URLs": paste LinkedIn URLs you already have and get full records.

## `searchType` (type: `string`):

Search mode: find people (linkedin.com/in profiles) or companies (linkedin.com/company pages).

## `role` (type: `string`):

Job title to look for, e.g. "CEO", "head of sales", "recruiter". People search: added to the query. Company search with "Find people at each company": the role searched at each company.

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

City, region or country, e.g. "Paris", "London", "Texas".

## `keywords` (type: `string`):

Industry, skills or any words, e.g. "SaaS", "marketing agency", "fintech", "shopify". When a search finds nothing, it is retried without the keywords, then without the location (said in the results), before ending with a free "0 results" row.

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

Maximum number of leads (people or companies) to return. Google pages hold about 10 results, so multiples of 10 work best. Minimum 5.

## `onlyNew` (type: `boolean`):

Search mode: skip the people / companies you already received from this Actor in previous runs (same Apify account, last 12 months) and keep searching until you have "Max results" NEW ones. Example: 20 growth marketers in Lille yesterday, run again with onlyNew for 20 more, no duplicate. Leads skipped are never charged.

## `scrapeResults` (type: `boolean`):

Also scrape each profile / company found (same full record as URL mode: experience, education, company size, etc.), billed per record like URL mode. Without it you get the Google data only: LinkedIn URL, name, position, company, location.

## `findEmail` (type: `boolean`):

Finds each person's professional email from their name and current company (company domain from the profile, otherwise guessed from the company name), then verifies it live over SMTP with the built-in email finder. Works in search mode (people) and in URL mode with Profile URLs. Billed only when a verified email is found ($9 / 1,000). Catch-all domains return a best guess with confidence "catch-all", free of charge.

## `requireEmail` (type: `boolean`):

People search only: deliver only people whose work email was found and verified. Profiles without one are skipped and not charged; the search looks at up to 3x more profiles to fill your list. Turns "Find emails" on.

## `companies` (type: `array`):

Skip the open search and find people at these companies: \[{"name": "SV Angel", "website": "svangel.com"}, …]. Uses "Job title / role" (e.g. partner, CEO) and "peoplePerCompany" (default 3). The website is used to find each person's email. Max 200 companies.

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

Used when "What do you want to do?" is "Scrape LinkedIn URLs": what kind of LinkedIn URLs are you providing?

## `urls` (type: `array`):

LinkedIn URLs matching the selected content type.

## `findPeopleAtCompanies` (type: `boolean`):

Company search only: for every company found, also search its employees with the job title in "Job title / role" (one extra search per company, up to "People per company" profiles, each billed as a search result).

## `peoplePerCompany` (type: `integer`):

With "Find people at each company": maximum profiles per company (5 to 10).

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

Two-letter Google country code used for the search (gl), e.g. us, fr, gb, de.

## `language` (type: `string`):

Two-letter Google interface language (hl), e.g. en, fr.

## Actor input object example

```json
{
  "mode": "search",
  "searchType": "people",
  "role": "Founder",
  "location": "London",
  "keywords": "SaaS",
  "maxResults": 20,
  "onlyNew": false,
  "scrapeResults": false,
  "findEmail": false,
  "requireEmail": false,
  "companies": [],
  "type": "Profile",
  "urls": [
    "https://www.linkedin.com/in/satyanadella/"
  ],
  "findPeopleAtCompanies": false,
  "peoplePerCompany": 10,
  "country": "us",
  "language": "en"
}
```

# Actor output Schema

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

All scraped records (JSON, CSV, Excel).

# 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 = {
    "mode": "search",
    "searchType": "people",
    "role": "Founder",
    "location": "London",
    "keywords": "SaaS",
    "companies": [],
    "type": "Profile",
    "urls": [
        "https://www.linkedin.com/in/satyanadella/"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("pnda/linkedin-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 = {
    "mode": "search",
    "searchType": "people",
    "role": "Founder",
    "location": "London",
    "keywords": "SaaS",
    "companies": [],
    "type": "Profile",
    "urls": ["https://www.linkedin.com/in/satyanadella/"],
}

# Run the Actor and wait for it to finish
run = client.actor("pnda/linkedin-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 '{
  "mode": "search",
  "searchType": "people",
  "role": "Founder",
  "location": "London",
  "keywords": "SaaS",
  "companies": [],
  "type": "Profile",
  "urls": [
    "https://www.linkedin.com/in/satyanadella/"
  ]
}' |
apify call pnda/linkedin-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,pnda/linkedin-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/btNUul6dyyuLVpSsd/builds/CMwZh34g7dc0GaG4L/openapi.json
