Email Extractor from Text: Emails, Phones & URLs from Any Text avatar

Email Extractor from Text: Emails, Phones & URLs from Any Text

Pricing

from $0.12 / 1,000 item extracteds

Go to Apify Store
Email Extractor from Text: Emails, Phones & URLs from Any Text

Email Extractor from Text: Emails, Phones & URLs from Any Text

Email extractor from text: extract email addresses, phone numbers (E.164), URLs, domains and social handles from pasted text, PDF, DOCX, XLSX, CSV, HTML and EML files or datasets. Finds obfuscated emails like name [at] domain [dot] com. Syntax check only, nothing is sent.

Pricing

from $0.12 / 1,000 item extracteds

Rating

0.0

(0)

Developer

Data Done Right

Data Done Right

Maintained by Community

Actor stats

0

Bookmarked

2

Total users

1

Monthly active users

6 days ago

Last modified

Security

Limited permissions

Share

This email extractor from text pulls email addresses, phone numbers (E.164), URLs, domains and social handles out of text you already have: pasted text, PDF, Word, Excel, CSV, HTML and email files (EML, MSG), or a text field of an Apify dataset. It also finds emails that people hide from bots, such as jane.doe [at] acme [dot] com. Use it to extract emails from text, to extract email addresses from a document, or as a quick email extractor for a pile of notes. It reads only what you give it: it does not crawl websites, send email or check mailboxes.

What you get:

  • One row per unique item: type, original value, normalised value (lowercase email, E.164 phone, clean URL), domain, count, source and a context snippet.
  • A per-source report (what was found in each text or file, and why a file failed) and a run summary.
  • Pay per item extracted, nothing else. Sources that fail or return nothing cost nothing.

To extract emails from websites instead of text you already have, use Domain List Email Extractor: Emails & Phones from Websites (see Related tools).

Privacy and responsible use

You supply the text, files and datasets. Only process data you are allowed to process, and follow the rules that apply to you (GDPR, CAN-SPAM, PECR and the terms of the source). This Actor does not send email, does not contact the addresses it finds, does no SMTP probing and no MX lookup. Email addresses are checked for syntax only. IBAN extraction is off by default because bank numbers are sensitive. Downloaded files are read in memory/temporary storage and deleted at the end of the run. The Actor never logs in anywhere, and refuses login-walled social sites and internal addresses.

What can it extract

TypeWhat you getNormalised as
emailRFC-practical syntax, plus name [at] domain [dot] com, name(at)domain.com, name at domain dot com, @, %40, mailto: links, zero-width characters. isRole flags info@, sales@, noreply@ and similar. obfuscated says whether it was hidden.lowercase local@domain
phoneNumbers valid for their country (libphonenumber), with country, national and international format and line typeE.164, for example +14155552671
urlhttp://, https:// and www. links, with trailing punctuation removedlowercase host, no fragment, no default port
domain (option)Domains of the emails and URLs that were foundbare domain, no www.
social and handle (option)Profile links on X/Twitter, Instagram, Facebook, LinkedIn, TikTok, YouTube, GitHub, Telegram, Threads, Pinterest, and plain @mentionsplatform:handle or @handle
iban (option, off by default)IBANs that pass the country length and mod-97 checksumcompact IBAN

How to extract emails from text

  1. Open the Actor and paste your text into Texts to scan. Each entry is one source (an entry can be a whole email thread).
  2. Leave Extract emails, Extract phone numbers and Extract URLs on, or switch on domains, social handles or IBANs.
  3. Run it, then download the dataset as JSON, CSV, Excel or HTML. Filter on the type column to get only emails.

How to extract email addresses from a PDF, Word or Excel file

Put the public links in File URLs: PDF, DOCX, XLSX, CSV, TXT, HTML, EML or MSG. The Actor downloads each file (up to the size limit), reads its text including table cells, headers and footers, and the links hidden behind words (mailto: links in PDFs, Word and HTML are read too). Scanned PDFs without a text layer need OCR first; this Actor does not do OCR and tells you so in the source report.

How to find obfuscated emails like name [at] domain [dot] com

Nothing to configure: de-obfuscation is always on. jane.doe [at] acme [dot] com, jane(at)acme.com, jane{at}acme{dot}org, anna DOT smith AT corp DOT de and sam@adatum.net come out as normal addresses with details.obfuscated: true. A bare at is only decoded when the domain also uses a spelled-out dot, so ordinary sentences such as "meet me at noon.com" are left alone.

How to extract emails from a dataset of another Actor

Pick the Dataset and set Dataset field (default text; dotted paths such as contact.notes work, and lists of strings are joined). Every dataset item becomes one source, so each row tells you which item it came from.

Input

Copy-paste input (this is the prefill):

{
"texts": [
"Contact our sales team at sales@acme-example.com or call +1 415 555 2671. For support write to support@acme-example.com (office hours 9-5) or phone +44 20 7946 0958. Our CEO Jane Doe can be reached at jane.doe [at] acme-example [dot] com, and press questions go to Press.Team@Acme-Example.com. More info: https://www.acme-example.com/contact"
]
}
FieldDefaultWhat it does
textsprefillTexts to scan, one source per entry
fileUrlsemptyPublic links to PDF, DOCX, XLSX, CSV, TXT, HTML, EML, MSG files
datasetId, datasetFieldempty, textScan a field of every item of an Apify dataset
extractEmailstrueEmail addresses
extractPhonestruePhone numbers in E.164
extractUrlstrueWeb links
extractDomainsfalseDomains of found emails and URLs
extractSocialHandlesfalseSocial profile links and @mentions
extractIbansfalseIBANs that pass the checksum
defaultRegionUS2-letter country for phone numbers without a + prefix (empty: only + numbers)
dedupeglobalglobal one row per unique item across sources, perSource, or off (every occurrence)
lowercaseEmailstrueLowercase the normalised email
skipRoleAccountsfalseDrop info@, sales@, support@, admin@, noreply@ and similar
domainAllowListemptyKeep only emails and URLs on these domains (subdomains included)
domainDenyListemptyDrop emails and URLs on these domains
contextChars60Characters of surrounding text on each side (0 switches it off)
maxItems1000Maximum rows returned and charged
maxSources1000Maximum texts, files and dataset items read
maxFileSizeMb25Larger files are skipped and reported
maxPdfPages200Pages read per PDF
maxCharsPerSource2,000,000Longer texts are cut, and the cut is reported
concurrency, timeoutSecs4, 30File download parallelism and timeout
proxyConfigurationnoneOptional, only for file URLs

Output

One dataset row per item. Real output of the prefill run (shortened to two rows):

[
{
"index": 3,
"type": "email",
"value": "jane.doe@acme-example.com",
"normalised": "jane.doe@acme-example.com",
"domain": "acme-example.com",
"count": 1,
"source": "text 1",
"sourceType": "text",
"sourceCount": 1,
"sources": ["text 1"],
"context": "...phone +44 20 7946 0958. Our CEO Jane Doe can be reached at jane.doe@acme-example.com, and press questions go to Press.Team@Acme-Example.com. Mor...",
"details": {"localPart": "jane.doe", "tld": "com", "isRole": false, "syntaxValid": true, "obfuscated": true}
},
{
"index": 6,
"type": "phone",
"value": "+44 20 7946 0958",
"normalised": "+442079460958",
"domain": null,
"count": 1,
"source": "text 1",
"sourceType": "text",
"sourceCount": 1,
"sources": ["text 1"],
"context": "...ite to support@acme-example.com (office hours 9-5) or phone +44 20 7946 0958. Our CEO Jane Doe can be reached at jane.doe@acme-example.c...",
"details": {"region": "GB", "countryCode": 44, "national": "020 7946 0958", "international": "+44 20 7946 0958", "numberType": "FIXED_LINE"}
}
]

Rows are ordered emails first, then phones, URLs, social handles, domains and IBANs, in order of first appearance. The context snippet shows the text after de-obfuscation.

Two key-value store records come with every run:

  • SUMMARY: totals by type, items returned and charged, filtered counts, notes about anything that went wrong.
  • SOURCES: one entry per text, file or dataset item with its status, file type, number of unique items found by type, and the error if it failed (for example download failed: HTTP 404).

How much does it cost

Pay per event: item-extracted = $0.00015 per output row ($0.15 per 1,000 rows). Sources that fail, are empty or are skipped produce no rows and cost nothing. maxItems caps both the rows and the cost.

ExampleRowsPrice
250 short texts with about 4 items each1,000about $0.15
A 300-page PDF directory with 10,000 unique emails and phones10,000about $1.50
A scraper dataset of 20,000 items with 100,000 unique contacts100,000about $15

Apify platform usage (compute) is included in the event price. With dedupe global you only pay for unique items, not for repeats.

Use cases

  • Clean a mailbox export, support thread or meeting notes into a contact list.
  • Pull the email addresses and phone numbers out of a PDF directory, a conference attendee list or a Word proposal.
  • Read the output of another scraper (a description or bio field) and add emails and handles to it.
  • Decode the "name [at] domain [dot] com" addresses on a copied staff page, then filter to the company domain.
  • Normalise phone numbers from mixed national formats to E.164 before importing into a CRM.

FAQ

Does it verify that an email address exists? No. It checks syntax only. There is no MX lookup, no SMTP probing and nothing is ever sent, so a syntactically valid address may still bounce. Run a dedicated verifier before a campaign.

Does it crawl websites? No. It parses text and files you give it. A file URL pointing to an HTML page is downloaded once and parsed as a document, with no links followed and no JavaScript run. To crawl company websites, use Domain List Email Extractor.

How does it decide a phone number is real? It uses Google's libphonenumber rules and keeps only numbers that are valid for their country. Numbers without a + prefix are read with defaultRegion. Long IDs, dates and order numbers are mostly ignored, but a digit string that happens to look like a valid number can still be returned; check the region and numberType fields.

Which files can it read, and what can it not read? PDF (text layer only, no OCR), DOCX, XLSX (values, not formulas), CSV/TXT and other text, HTML, EML and MSG. It does not unpack ZIP archives, read legacy .doc/.xls files or password-protected PDFs, and it does not read images. Failed files are listed in SOURCES with the reason.

Are role accounts and free-mail addresses flagged? Role accounts (info@, sales@, noreply@ and about 60 more) get isRole: true and can be skipped with skipRoleAccounts. Free-mail providers are not flagged; use domainDenyList with gmail.com and similar to drop them.

Is my text stored or sent anywhere? No third-party service is called. The text is processed inside the Actor run; items are written to your own dataset. File URLs are downloaded from the public internet from the Actor, and internal and private addresses are blocked.

Limits

  • Syntax check only for emails (see above). IBANs only for the countries in the IBAN registry list built in.
  • Names are not extracted; a row is an address, number or link, with the surrounding text in context.
  • Cut-offs are reported: maxCharsPerSource for long texts, maxPdfPages, maxFileSizeMb, maxItems, maxSources.
  • With dedupe global, source is the first source and sources lists at most 25 sources (sourceCount has the real number).

Use with the Apify API, MCP, n8n and Make

Run it from any tool that can call the Apify API. In n8n use the Apify node (Run Actor, then Get Dataset Items), in Make use the Apify app, and for AI agents use the Apify MCP server, which exposes this Actor with its input schema.

Python:

from apify_client import ApifyClient
client = ApifyClient("<YOUR_APIFY_TOKEN>")
run = client.actor("<your-username>/email-extractor-from-text").call(run_input={
"texts": ["Write to jane.doe [at] acme-example [dot] com or call +1 415 555 2671"],
"skipRoleAccounts": True,
})
for item in client.dataset(run["defaultDatasetId"]).iterate_items():
print(item["type"], item["normalised"])

JavaScript:

import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: '<YOUR_APIFY_TOKEN>' });
const run = await client.actor('<your-username>/email-extractor-from-text').call({
fileUrls: ['https://example.com/contacts.pdf'],
extractDomains: true,
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items.map((i) => `${i.type} ${i.normalised}`));
  • Domain List Email Extractor: Emails & Phones from Websites to find contact details by crawling company websites.
  • Phone Number Validation & Lookup: Format, Carrier, Line Type to check and enrich the phone numbers you extracted.
  • Merge Datasets & Dedupe: Combine, Filter, Export CSV & Excel to merge the extracted rows with other datasets and remove duplicates.