# Website Contact & Imprint Extractor (Emails, Phones, Socials) (`veedel_digital/contact-extractor`) Actor

Get emails, phone numbers and social media profiles from any list of websites, plus company data from the German imprint (Impressum): company name, address, managing directors, VAT ID and trade register. No proxies, pay per website.

- **URL**: https://apify.com/veedel_digital/contact-extractor.md
- **Developed by:** [Tim Tonat](https://apify.com/veedel_digital) (community)
- **Categories:** Lead generation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $4.00 / 1,000 websites

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?

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

### What does Website Contact & Imprint Extractor do?

This Actor **finds contact details and company data on any list of websites**. Give it domains or URLs and get **one row per website** with:

- **Email addresses** from mailto links and page text, including simple obfuscation like `info [at] example [dot] com`
- **Phone numbers**, as written and normalized
- **Social media profiles**: LinkedIn, XING, Facebook, Instagram, X/Twitter, YouTube, TikTok, GitHub, Pinterest
- **Contact page**, **imprint page** and **careers page** URLs
- A **primary email** for the first contact: `info@` before personal addresses, `newsletter@` or `jobs@` last
- **Company data from the imprint** (Impressum, required on German, Austrian and Swiss business websites): **company name, address, managing directors, VAT ID, register court and trade register number (HRB)**

It only visits the homepage and the few pages that matter (imprint, contact, about, privacy), so runs are fast and cheap. No proxies, no browser.

### Why use this contact extractor?

- **Enrich lead lists**: you have company websites, you need emails, phone numbers and the legal company name
- **Verify companies in Germany, Austria and Switzerland**: get the official company name, VAT ID and HRB number straight from the imprint
- **CRM cleanup**: fill in missing LinkedIn or XING pages and phone numbers
- **Agencies**: check which client sites are missing an imprint or contact page
- **Pay per website**: one price per website, no matter how many pages are visited

### What data does it return?

| Field | Description |
|---|---|
| `domain` | Domain without `www` |
| `primaryEmail` | Best address for a first contact (own domain, general address first) |
| `emails` | All email addresses found on the visited pages, sorted the same way |
| `phones` | `raw` as written on the site and `normalized` (international format if the site gives a country code, otherwise digits only) |
| `socialProfiles` | One profile per network, share buttons are ignored |
| `contactPageUrl`, `imprintUrl`, `careersPageUrl` | Contact, imprint and careers page |
| `imprint` | `companyName`, `address` (street, postal code, city), `managingDirectors`, `vatId`, `registerCourt`, `registerNumber`, `sourceUrl` |
| `pagesVisited` | Pages loaded for this website |
| `error` | Why the website could not be processed |

Imprint fields are read with rules, not guessed. Each field comes from the imprint page, then the contact page, then the homepage. If a value is not clearly found, it stays `null`. German, Austrian (Firmenbuch, `FN 123456a`) and Swiss (`CH-…` register number, `CHE-…` UID) imprints are supported, and EU VAT IDs are recognized.

### How to extract contacts from websites

1. Click **Try for free**.
2. Paste your websites into **Websites**, one per line (`example.com` is enough).
3. Optional: change **Max pages per website** (default 5).
4. Click **Start**.
5. Download the results as JSON, CSV, Excel or HTML, or send them to Google Sheets.

### How much does it cost?

This Actor uses **pay per event**: a fixed price **per processed website**, and **platform usage is included**. The current price is shown in the **Pricing** tab. Websites that can't be loaded (DNS error, HTTP error, blocked by robots.txt), bot-protection pages, JavaScript-only homepages without content and parked domains are not charged.

### Input

See the **Input** tab for all options.

```json
{
    "urls": ["example.de", "https://www.example.com"],
    "maxPagesPerSite": 5,
    "respectRobotsTxt": true
}
```

### Output

You can download the dataset in various formats such as JSON, HTML, CSV, or Excel.

```json
{
    "url": "https://www.example.de/",
    "domain": "example.de",
    "primaryEmail": "info@example.de",
    "emails": ["info@example.de", "jobs@example.de"],
    "phones": [{ "raw": "+49 221 123456-0", "normalized": "+492211234560" }],
    "socialProfiles": {
        "linkedin": "https://www.linkedin.com/company/example",
        "instagram": "https://www.instagram.com/example"
    },
    "contactPageUrl": "https://www.example.de/kontakt/",
    "imprintUrl": "https://www.example.de/impressum/",
    "careersPageUrl": "https://www.example.de/karriere/",
    "imprint": {
        "sourceUrl": "https://www.example.de/impressum/",
        "companyName": "Example Haustechnik GmbH",
        "vatId": "DE123456789",
        "registerCourt": "Amtsgericht Köln",
        "registerNumber": "HRB 12345",
        "managingDirectors": ["Max Mustermann"],
        "address": { "street": "Hauptstraße 12", "postalCode": "50667", "city": "Köln" }
    },
    "pagesVisited": 4,
    "error": null
}
```

### Related Actors

Combine it with the SEO Site Audit: find out who runs a website, then show them what to fix.

- [SEO Site Audit & Broken Link Checker](https://apify.com/veedel_digital/seo-audit): crawl a whole website and find on-page SEO issues and broken pages
- [PageSpeed Insights & Core Web Vitals Bulk Audit](https://apify.com/veedel_digital/pagespeed-audit): Lighthouse scores and real-user Core Web Vitals for many URLs
- [Structured Data, Schema.org & Open Graph Extractor](https://apify.com/veedel_digital/structured-data): extract JSON-LD, schema.org types and Open Graph tags from many pages
- [PDF to Text with OCR](https://apify.com/veedel_digital/pdf-to-text): extract text from PDFs in bulk, scanned pages included

### FAQ

#### Is it legal to extract contact data?

The Actor only reads information that companies publish themselves, usually because the law requires it (the imprint). **You are responsible for how you use the data.** Personal data such as names or personal email addresses is protected by the GDPR. In Germany, sending advertising emails or making advertising calls without prior consent is generally not allowed (§ 7 UWG). Use the results for research, verification and data enrichment, not for unsolicited mass mailing.

#### Why are some fields empty?

Some websites load their content only with JavaScript in the browser. The Actor reads the HTML the server delivers, like most crawlers do, so such sites return few or no results. Imprint fields also stay empty when the information is shown as an image or in an unusual format. Shopify shops publish their imprint under `/policies/`, which their `robots.txt` blocks: disable *Respect robots.txt* to read it.

#### Does it work outside Germany?

Emails, phones and social profiles work for websites in any language. The imprint fields are designed for Germany, Austria and Switzerland (Impressum, HRB, Amtsgericht, USt-IdNr.), and some English legal notices are recognized too.

#### Will it overload websites?

No. It visits at most *Max pages per website* pages per site and follows `robots.txt` by default.

#### Something does not work

Please open an issue in the **Issues** tab with the website and the run ID. You can also start the Actor programmatically from the **API** tab.

# Actor input Schema

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

Websites or domains, one per line (e.g. example.com or https://www.example.com).

## `maxPagesPerSite` (type: `integer`):

Homepage plus the most relevant subpages (imprint, contact, about, privacy). Price is per website, not per page.

## `respectRobotsTxt` (type: `boolean`):

Skip pages disallowed by the site's robots.txt.

## Actor input object example

```json
{
  "urls": [
    "https://www.heise.de",
    "apify.com"
  ],
  "maxPagesPerSite": 5,
  "respectRobotsTxt": true
}
```

# Actor output Schema

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

Dataset with contacts and imprint data per website

# 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 = {
    "urls": [
        "https://www.heise.de",
        "apify.com"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("veedel_digital/contact-extractor").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 = { "urls": [
        "https://www.heise.de",
        "apify.com",
    ] }

# Run the Actor and wait for it to finish
run = client.actor("veedel_digital/contact-extractor").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 '{
  "urls": [
    "https://www.heise.de",
    "apify.com"
  ]
}' |
apify call veedel_digital/contact-extractor --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,veedel_digital/contact-extractor"
        }
    }
}
```

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/XSNLakIPOx4zrpLT3/builds/MtOeCv2koAYRyAjJW/openapi.json
