Website Email & Contact Scraper — $3/1K Sites, Phones
Pricing
from $2.10 / 1,000 website with contacts
Website Email & Contact Scraper — $3/1K Sites, Phones
[$3/1K sites with contacts] Website contact scraper and email extractor: paste company domains and get one row per site with emails, phones in E.164, LinkedIn, Facebook, Instagram and 6 more socials, the contact page and an MX check. Sites with no contacts are free. No API key.
Pricing
from $2.10 / 1,000 website with contacts
Rating
5.0
(1)
Developer
apifry
Maintained by CommunityActor stats
2
Bookmarked
11
Total users
6
Monthly active users
3 days ago
Last modified
Categories
Features
Share
Website Email & Contact Scraper — Emails, Phones & Socials
Paste a list of company websites and get one clean lead row per website: emails, phone numbers, social profiles and the contact page URL. No API keys, no login. A fast plain-HTTP crawl by default, plus an optional browser mode for websites that only show contacts after JavaScript runs.
You only pay for websites where at least one email or phone number was found. Sites with no contacts, unreachable sites and sites behind bot protection are still listed in the results (so you know what happened) but cost nothing.
Tested on 100 real company websites
Same 100 websites, same day, compared with the most-used contact scraper in Apify Store (which charges per page), both limited to 8 pages per site:
| This Actor | Per-page contact scraper | |
|---|---|---|
| Websites with an email | 74 | 66 |
| Unique emails found | 587 | 339 |
| Placeholder / broken addresses | 0 | 3 |
| Price for these 100 websites | $0.23 | $1.44 |
You pay for the 78 websites where contacts were found, not for 732 pages. Honest notes: one run on mostly mid-size and large companies (SaaS, hosting, law firms, hotels, restaurants, brands, nonprofits in the US and Europe); the other scraper got past bot protection on more sites (97 vs. 86 reachable); about a quarter of our emails are on the company's other domains or its partners' — turn on Only emails on the website's own domain if you don't want them.
Website email & contact extractor: what you get per domain
| Field | Example |
|---|---|
domain | acme.de |
status | ok, no_contacts, unreachable, blocked, invalid_input |
primaryEmail | info@acme.de — the best first-touch address |
emails | ["info@acme.de", "anna.schmidt@acme.de"] |
emailDetails | type (generic / personal), same domain as the site, MX check, page where it was found |
phones | ["+493012345670"] — normalized to international E.164 format |
linkedin, facebook, instagram, twitter, youtube, tiktok, pinterest, telegram, whatsapp | company profile URLs |
contactPageUrl | https://acme.de/kontakt |
pagesScraped | 3 |
renderedWithBrowser | false — true if contacts were found only with the browser option |
Results can be downloaded as CSV, Excel or JSON, or sent to Google Sheets, HubSpot, Make, Zapier and n8n through Apify integrations.
Why this extractor finds more (and less junk)
- Goes straight to the right pages. Besides the homepage it opens the pages most likely to list contacts — Contact, About, Team, Impressum, Mentions légales, Aviso legal and their equivalents in 10+ languages — instead of crawling a blog.
- Reads hidden emails. Cloudflare-protected addresses (
[email protected]),name [at] company [dot] com, HTML entities and emails inside JSON/scripts. - Drops junk. No
logo@2x.png, tracking IDs,noreply@,you@example.comor placeholder addresses. - Checks deliverability. Every email domain is checked for mail servers (MX), so dead addresses are flagged.
- Phones you can dial. Numbers from
tel:links and page text are validated and converted to+CountryCode…. The country comes from the domain ending (.de→ Germany); for.com,.org,.ioand similar it is detected from the site itself (language,+44numbers, postcodes). You can also set it (GB,DE,US;UKworks too). - Handles real-world input.
www.,http://, paths and duplicates are normalized, redirects to a new domain are followed, international domains are supported.
Use cases
- Cold outreach. You have a list of target companies from Google Maps, a directory or a trade-show exhibitor list. Get a generic address (
info@,sales@) and named people's emails for each one, ready for your email tool. - CRM enrichment. Export the websites of accounts with no contact data from HubSpot, Pipedrive or a spreadsheet, run them here and import the results back. One row per website keeps the join simple.
- Partner and supplier lists. Check hundreds of distributor, agency or supplier websites at once and see who publishes a contact email, a phone number or a LinkedIn page — and which websites are down.
- List cleanup. Spot dead domains (
unreachable), websites that redirect to another company, and emails whose domain can no longer receive mail (mxValid: false) before you send a campaign.
How to use it
- Add websites to Websites — one domain or URL per line (thousands per run are fine).
- Optionally adjust Max pages per website (default 8) and the other options.
- Many websites came back
no_contactsorblocked? Turn on Render JavaScript for sites with no contacts (browser). Only those websites are opened again in a headless browser, and they are billed at the browser price only if contacts are found. Give the run at least 2 GB of memory.
- Many websites came back
- Click Start and download the results.
Input example
{"urls": ["acme.de", "https://www.example-bakery.co.uk/about"],"maxPagesPerDomain": 8,"includePhones": true,"includeSocials": true,"onlySameDomainEmails": false,"verifyMx": true,"renderJavaScript": false}
Output example
{"domain": "acme.de","status": "ok","primaryEmail": "info@acme.de","emails": ["info@acme.de", "anna.schmidt@acme.de"],"phones": ["+493012345670"],"linkedin": "https://www.linkedin.com/company/acme-gmbh","instagram": "https://www.instagram.com/acme.de","contactPageUrl": "https://acme.de/kontakt","pagesScraped": 3}
Pricing
| Event | When | Price |
|---|---|---|
| Website with contacts | Email or phone found with the normal (fast) crawl | $3.00 / 1,000 websites |
| Website with contacts (browser) | Contacts found only after rendering the site in a browser — only if you turn this option on | $12.00 / 1,000 websites |
Each website is billed at most once. Websites where nothing was found, unreachable or blocked websites are free — also when the browser was tried. The renderedWithBrowser field in the results shows which price applied. You can set a maximum spend per run in the run options; the extractor stops cleanly when the limit is reached.
Use with the API, AI agents and MCP
from apify_client import ApifyClientclient = ApifyClient("<YOUR_API_TOKEN>")run = client.actor("apifry/website-contact-extractor").call(run_input={"urls": ["acme.de"]})for item in client.dataset(run["defaultDatasetId"]).iterate_items():print(item["domain"], item["primaryEmail"], item["phones"])
The extractor also works as a tool for AI agents through the Apify MCP server.
🤖 For AI Agents & LLM Apps
Purpose. Turns a list of company websites into contact data: one dataset row per input website with its public emails, phone numbers and social profile links. Use it to answer "how do I contact this company?", to enrich a list of domains for a CRM, or as the second step after a tool that returns company websites.
Minimal input.
{ "urls": ["apify.com", "https://www.monzo.com/contact"] }
Bare domains, URLs with paths and www. all work; duplicates are processed once.
Output. One row per website with: input, domain, url, status, primaryEmail, emails, emailDetails (email, type, sameDomain, mxValid, foundOn), phones (E.164), phoneDetails (phone, raw, source, foundOn), linkedin, facebook, instagram, twitter, youtube, tiktok, pinterest, telegram, whatsapp, socials, contactPageUrl, pagesScraped, renderedWithBrowser, error, scrapedAt.
Behaviors an agent should know.
statusisok,no_contacts,blocked,unreachableorinvalid_input. Onlyokrows are charged; every other row is free and explains why there is no data.- Up to 8 pages per website by default (
maxPagesPerDomain, max 50); contact, about, team and imprint pages are visited first. - Phone numbers without a
+are read in the country of the website (domain ending or the site itself). SetphoneCountry(GB,DE,US) when all websites are from one country. onlySameDomainEmails: truekeeps only addresses on the company's own domain — use it when you need business emails, not partners or service providers.- An email with
mxValid: truemeans its domain accepts mail; it does not prove the mailbox exists. - JavaScript-only websites may return
no_contacts; rerun just those withrenderJavaScript: true(billed as a separate, higher-priced event only when the browser finds contacts). - No login, cookies or API keys of the target sites are used — only public pages.
- Proxy: only the datacenter Apify Proxy (or your own
proxyUrls); residential groups andapifyProxyCountryare ignored with a log warning. Memory: 1 GB default, 2 GB forrenderJavaScript, maximum 4 GB.
FAQ
How do I extract emails from a list of domains in bulk? Paste the whole list into Websites (in Console, Bulk edit takes one domain or URL per line; through the API, pass the urls array). Thousands of domains per run are fine, and duplicates such as www. and non-www versions are processed once. You get one row per domain with its emails, phones and social profiles; export it as CSV or Excel from the Output tab. Domains with no contacts stay in the list with a status and cost nothing.
Do I need proxies? Usually not. Sites that answer with bot protection are automatically retried once through the datacenter Apify Proxy. If many sites still come back as blocked, turn on the browser option (it gets past some bot checks) or add your own proxy URLs in the input. Residential Apify Proxy is not supported: the price per website already includes the platform costs, and residential traffic would cost more than the site itself. Blocked websites are never charged.
How much memory does a run need? The default 1 GB is enough for the plain crawl, 2 GB for the browser option. Runs are capped at 4 GB — more memory does not make this Actor faster.
What about very long lists? Runs time out after 1 hour by default. Before the timeout the extractor stops cleanly and tells you how far it got; resurrect the run (Actions → Resurrect) and it continues where it stopped without charging twice for any website.
Why is a website no_contacts? The site doesn't publish an email or phone on its main pages (some only have a contact form), or loads its content with JavaScript only. You are not charged for it. For JavaScript-only sites, turn on the browser option and run those websites again.
Is it legal? See Responsible use below.
Responsible use
The extractor only opens publicly available pages of the websites you list. It does not log in, solve CAPTCHAs or bypass paywalls, and it does not guess or generate email addresses. Personal data such as named employees' emails is still personal data: you are responsible for having a lawful basis to process it and for following the rules that apply to your outreach (for example GDPR in the EU/UK and CAN-SPAM in the US). If you are unsure, ask a lawyer.
Website Email & Contact Scraper not working?
Every website gets a row with a status, so you always see what happened. Only ok rows are charged.
- Many
no_contacts. The site shows no email or phone on its main pages (often only a contact form), or loads its content with JavaScript. Raise Max pages per website or rerun just those sites with Render JavaScript for sites with no contacts (browser) turned on and at least 2 GB of memory. - Many
blocked. The sites answered with bot protection. Keep Retry blocked websites through Apify Proxy on, try the browser option, or add your own proxy URLs. unreachable. The domain does not answer or does not exist (dead domains, typos). Check theerrorcolumn.- Phones look wrong or missing. Set Default phone country (
GB,DE,US) when all your websites are from one country. - Emails of other companies. Turn on Only emails on the website's own domain.
- The run timed out on a long list. Resurrect it (Actions → Resurrect) — it continues where it stopped and never charges twice for a website.
Support
Something missing, wrong or unclear? Open an issue on the Issues tab — include the website and what you expected to see. Issues are answered within one business day. Need a custom version (other fields, other sources, a scheduled pipeline)? Open an issue with the details too.
If the extractor saved you time, a short review on the Reviews tab helps other users find it — and tells us what to improve next.
You might also like
- Trustpilot Reviews Scraper — what customers say about the companies on your list: Trustpilot reviews in every language.