# Email, Phone and IP Risk API - Digital Footprint Lookup (`nabeelbaghoor/email-phone-ip-risk-api`) Actor

Check the digital footprint behind an email address, phone number or IP: which of 290 plus online platforms it is registered on, a fraud risk score, breach history, domain and DNS records, carrier, line type and SIM swap signals, and proxy, VPN and Tor detection. Pay per result.

- **URL**: https://apify.com/nabeelbaghoor/email-phone-ip-risk-api.md
- **Developed by:** [Nabeel Hassan](https://apify.com/nabeelbaghoor) (community)
- **Categories:** Business, Developer tools, Lead generation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

$15.00 / 1,000 results

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?

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

## Email, Phone and IP Risk API - Digital Footprint Lookup

Give it an email address, a phone number or an IP, and get back what the internet already knows about it: where it is registered, whether it has ever been breached, who carries it, and how risky it looks. One flat row per lookup.

### What this actor does

- **Finds the digital footprint behind an identifier.** The provider checks an email address or phone number against more than 290 consumer and business platforms and reports which ones it is registered on. This actor lifts that out of the nested response into two usable columns: a count, and a flat sorted list of platform names you can filter on.
- **Scores fraud risk.** Every lookup returns a risk score built from the provider's consortium network, so you get a number to sort by rather than a pile of raw attributes to interpret yourself.
- **Verifies email deliverability and domain health.** Deliverable, valid format, full inbox, catch-all, minimum account age, randomness score, and the whole domain picture: registrar, creation and expiry dates, MX validity, DMARC enforcement, strict SPF, suspicious TLD, free provider and disposable flags.
- **Checks breach history.** How many known breaches the address appears in, the first and last one, the named breach list, and whether it is listed in Have I Been Pwned.
- **Identifies phone numbers properly.** Carrier, line type, country, validity, subscriber name, roaming and porting status, and a SIM swap signal, which is the one that matters when a number is being used as a second factor.
- **Detects proxies, VPNs and Tor.** The IP service separates web proxy, public proxy, data centre proxy, residential proxy, consumer privacy network and Tor rather than collapsing them into one flag, because a corporate VPN and a residential proxy are not the same finding.
- **Refuses inputs that cannot work, before they cost anything.** Every request is charged by the provider whether or not it returns a result, so an address with no at sign, a string with too few digits to be a phone number, or something that is not an IP is refused locally and recorded as a refusal instead of being paid for.
- **Names the region problem instead of hiding it.** Keys are issued per region and the regions are separate installations, so a key from the wrong one is refused with exactly the message a wrong key gets. When that happens, the error here says so.
- **Never charges for a miss.** Only rows carrying a resolved result are billed.

### Input

| Field | What it does |
| --- | --- |
| `mode` | Which service to run: email, phone or IP. |
| `queries` | The values to look up, one per line. |
| `region` | Which regional deployment your key belongs to. |
| `ipInclude` | Extra blocks the IP service attaches on request. |
| `flagsTimeframeDays` | How far back to look for IP flags. |
| `providerConfig` | JSON settings passed to the provider as written. |
| `minRiskScore` | Keep only rows scoring at or above this. |
| `maxRiskScore` | Keep only rows scoring at or below this. |
| `requireDeliverable` | Keep only deliverable email addresses. |
| `excludeDisposable` | Drop throwaway domains and numbers. |
| `excludeFreeProviders` | Drop free consumer mail providers. |
| `requireValidPhone` | Keep only numbers confirmed valid. |
| `lineTypes` | Keep only these phone line types. |
| `excludeProxies` | Drop proxies, VPNs and Tor nodes. |
| `countries` | Keep only these countries. |
| `minRegistrations` | Keep only rows with this many platform registrations. |
| `registeredOn` | Keep only rows registered on these named platforms. |
| `minBreachCount` | Keep only rows in this many breaches. |
| `requestsPerMinute` | Pace the run under your plan's rate limit. |
| `skipNotFound` | Leave misses and refusals out of the dataset. |
| `maxResults` | Hard cap on rows, and therefore on spend and run time. |
| `apiKey` | Your own license key. Stored as a secret. |

### Example output

```json
{
  "found": true,
  "mode": "email-risk",
  "query": "user@example.com",
  "lookupId": "b3d1f0c2-0a1b-4c2d-9e3f-5a6b7c8d9e0f",
  "email": "user@example.com",
  "riskScore": 12.5,
  "deliverable": true,
  "validFormat": true,
  "fullInbox": false,
  "minimumAgeMonths": 96,
  "earliestProfileDate": "2018-03-11",
  "emailRandomnessScore": 8.2,
  "domain": "example.com",
  "tld": "com",
  "isFreeProvider": false,
  "isDisposable": false,
  "isCustomDomain": true,
  "acceptsAll": false,
  "hasValidMx": true,
  "dmarcEnforced": true,
  "spfStrict": true,
  "suspiciousTld": false,
  "domainRegistered": true,
  "domainRegistrar": "Example Registrar Inc",
  "domainCreated": "1995-08-14",
  "domainExpires": "2027-08-13",
  "websiteExists": true,
  "registrationCount": 14,
  "registeredOn": ["airbnb", "amazon", "github", "linkedin", "spotify"],
  "breachCount": 3,
  "firstBreach": "2016-05-21",
  "lastBreach": "2023-11-02",
  "listedInHaveIBeenPwned": true,
  "breaches": ["Collection1", "LinkedIn", "Dropbox"],
  "fraudHistoryHits": 0,
  "associatedDomainCount": 2,
  "associatedDomains": ["example.com", "example.net"],
  "error": null,
  "raw": { }
}
```

### Frequently asked questions

#### What is a digital footprint lookup and why is it better than a validity check?

A validity check tells you whether an address can receive mail. A digital footprint lookup tells you whether a person has been using it. The provider checks the identifier against more than 290 consumer and business platforms and reports where it is registered, so an address with accounts on twenty services and an eight year history reads very differently from one that is technically deliverable and has never been used anywhere. For fraud screening that difference is the whole signal, and it is the thing a syntax and MX check cannot see.

#### What is the difference between the three services?

They take three different kinds of input and answer three different questions, so a run uses one at a time. The email service returns deliverability, domain and DNS health, breach history and platform registrations. The phone service returns carrier, line type, validity, porting and SIM swap signals, plus its own platform registrations. The IP service returns location, network, and a full proxy, VPN and Tor breakdown. All three return a risk score on the same scale, so a mixed set of runs still sorts together.

#### What does the risk score mean?

It is the provider's own aggregate, drawn from its consortium network of member data plus the attributes in the response, on a scale where higher is riskier. The useful way to use it is not as a verdict but as a sort order: run your list, sort by score, and look at the top of it. If you need a hard cutoff, set the minimum or maximum score filters and let the actor apply it, so the dataset arrives already reduced to the rows you were going to keep.

#### Why does the actor refuse some of my inputs before sending them?

Because this provider charges per request whether or not the request returns anything. A string with no at sign is not an email address, a string with fewer than seven digits is not a phone number, and something that is neither four dotted numbers nor a colon separated hextet run is not an IP address. Sending those costs money and teaches you nothing. They are refused locally, cost nothing, and are written to the dataset as refusals with the reason, so a run that ignored a third of its list does not look like a run whose provider found nothing. The checks are deliberately shallow: anything that could plausibly be real is sent, and the provider gets the final say.

#### Why do I keep getting told my API key is invalid when it is not?

Almost always the region. This provider runs separate installations in Europe, the United States, the Middle East and Asia Pacific, and a key issued against one is refused by all the others with the same error text a genuinely wrong key gets. Set the region field to the one your account was created in. The credential error from this actor names the region it used, so the message tells you what to check.

#### What are the platform registration columns actually good for?

Two things. As a count, it is a fast liveness test: a minimum registration filter of five or ten removes freshly minted identities from a signup list in one pass. As a list, it is a targeting signal: filtering to addresses registered on a particular professional network gives you a segment that no firmographic field can express, because it describes what the person does rather than where they work.

#### Can I use a setting the provider added after this actor shipped?

Yes. The provider settings field takes a JSON object and sends it exactly as written, with no vocabulary check in the way. The configuration keys differ per service and are not published as a fixed list, so rather than guess at a set and quietly drop anything unrecognised, this actor passes through whatever you give it. A new provider option works the day it ships.

#### What is the rate limit and why is the default so low?

The provider allows two requests per second on a trial account and twenty on a production one. The default pacing here is 100 requests per minute, which sits under the trial limit, because a run that trips the limiter on the third request is worse than a run that takes a little longer. On a production account, raise it towards 1200 a minute.

#### Do I need my own API key?

Yes. This actor does not include data access. You use your own license key from SEON, which is the provider whose digital footprint and risk API this actor calls, taken from the organisation page of your provider account and pasted into the `apiKey` field, where it is stored as an Apify secret. Your own plan, credit balance and terms apply.

#### What happens when a lookup returns nothing?

A negative answer is a result, not a miss: the provider telling you an address is undeliverable or a number is invalid is exactly the question you asked, so that row is written and billed like any other. A miss is a lookup the provider had no record for at all, and a refusal is an input that never left this actor. Both are written with `found: false` and are never billed. Set `skipNotFound` to true to leave them out entirely.

#### How much does a run cost?

Pricing is pay per result: you are charged for each value resolved into the dataset, and never for misses, for locally refused inputs, for rows dropped by the filters, or for duplicates. Apify platform usage is included in the per-result price. Your own API provider's credit balance is separate and billed by them.

### Keyword map

email risk API, digital footprint API, social media lookup by email, email to social profiles, reverse email lookup, email verification API, disposable email detection, catch all detection, DMARC and SPF check, data breach lookup API, have i been pwned API, phone risk API, phone number lookup, carrier lookup, line type detection, SIM swap detection, number porting check, IP reputation API, proxy detection API, VPN detection, Tor exit node check, residential proxy detection, data centre IP detection, fraud detection API, account takeover prevention, bot signup prevention, KYC screening, identity risk score, chargeback prevention, payment fraud screening

# Actor input Schema

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

Which of the three services to call. Each one takes a different kind of input, so a run looks up one kind of value at a time: email addresses, phone numbers, or IP addresses. Anything in the list that cannot be the kind this mode expects is refused before it is sent, since the provider charges per request either way.

## `queries` (type: `array`):

The email addresses, phone numbers or IP addresses to look up, one per line, matching the service chosen above. Phone numbers should include the country code; spaces, plus signs, brackets and dashes are all fine and are stripped before sending. Duplicates are looked up once.

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

Which regional deployment your account lives on. This matters more than it looks: the regions are separate installations and a key issued in one is refused by every other one with the same message a wrong key gets. If every lookup comes back saying the key is invalid and you are sure it is not, this is the setting to change.

## `ipInclude` (type: `array`):

Extra sections the IP service will attach when asked for them by name. History adds what the provider has seen this address do before, flags adds the rule hits behind the score, and id returns the lookup identifier. Has no effect on the email and phone services.

## `flagsTimeframeDays` (type: `integer`):

How far back the IP service should look when returning flags. Only used when flags are requested above. Leave empty for the provider's own default window.

## `providerConfig` (type: `object`):

A JSON object of provider settings, merged into the request exactly as written. The provider's configuration keys differ per service and are not published as a fixed list, so nothing is guessed at here: whatever you write is sent as given. Use this to switch a module on or off, or to set a timeout, without waiting for a named field. Leave empty for the provider's defaults.

## `minRiskScore` (type: `integer`):

Only keep rows scoring at or above this. Use it to turn a run into a review queue containing only what is actually suspicious. Leave at zero to keep every score.

## `maxRiskScore` (type: `integer`):

Only keep rows scoring at or below this. The mirror of the minimum, and the one to use when you are building a clean list rather than a review queue. Leave at zero to keep every score.

## `requireDeliverable` (type: `boolean`):

In the email service, drop addresses the provider did not mark deliverable. Has no effect on the other two services.

## `excludeDisposable` (type: `boolean`):

Leave out throwaway email domains and disposable phone numbers, which are the usual signature of a signup that was never meant to be reachable.

## `excludeFreeProviders` (type: `boolean`):

Leave out addresses on free consumer mail providers, keeping only company domains. Useful when the list is meant to be a business one.

## `requireValidPhone` (type: `boolean`):

In the phone service, drop numbers the provider could not confirm as valid. Has no effect on the other two services.

## `lineTypes` (type: `array`):

Only keep phone rows whose line type matches one of these, written as the provider names them, such as mobile or landline. Matching ignores capitalisation. Leave empty to keep every type.

## `excludeProxies` (type: `boolean`):

In the IP service, drop addresses flagged as any kind of proxy, VPN, or Tor node. Has no effect on the other two services.

## `countries` (type: `array`):

Only keep rows resolving to one of these two-letter country codes. Applies to the phone and IP services, which are the two that return a country. Leave empty to keep every country.

## `minRegistrations` (type: `integer`):

Only keep rows registered on at least this many online platforms. This is the single best proxy for whether an identity is real: an address with a footprint on twenty services has a history, and one with none was very likely created this morning. Leave at zero to keep every row.

## `registeredOn` (type: `array`):

Only keep rows registered on every platform named here, written as the provider names them, such as linkedin or spotify. Matching ignores capitalisation. Leave empty to skip this check.

## `minBreachCount` (type: `integer`):

Only keep rows appearing in at least this many known data breaches. Leave at zero to keep every row.

## `requestsPerMinute` (type: `integer`):

Pace the run so it stays under whatever rate your plan allows. The provider allows two requests a second on a trial account and twenty on a production one, so the default of 100 a minute sits safely under the trial limit. Raise it to about 1200 on a production account to finish a long list sooner.

## `skipNotFound` (type: `boolean`):

Leave values the provider returned nothing for, and inputs refused before they were sent, out of the dataset. Off by default, because knowing which of your values were unusable is usually the point. Misses are never charged for either way.

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

Stop after this many rows. This is the cap on both spend and run time.

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

Your own license key for the digital footprint and risk API, taken from your provider account. Keys are issued per region, so make sure the region above matches the one your account sits on. Stored as a secret.

## Actor input object example

```json
{
  "mode": "email-risk",
  "queries": [
    "user@example.com"
  ],
  "region": "eu",
  "ipInclude": [],
  "minRiskScore": 0,
  "maxRiskScore": 0,
  "requireDeliverable": false,
  "excludeDisposable": false,
  "excludeFreeProviders": false,
  "requireValidPhone": false,
  "excludeProxies": false,
  "minRegistrations": 0,
  "minBreachCount": 0,
  "requestsPerMinute": 100,
  "skipNotFound": false,
  "maxResults": 100
}
```

# Actor output Schema

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

One row per lookup, carrying the risk score, the platform registration footprint, breach and fraud history, and the email, phone or IP attributes for the service that was run.

# 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 = {
    "queries": [
        "user@example.com"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("nabeelbaghoor/email-phone-ip-risk-api").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 = { "queries": ["user@example.com"] }

# Run the Actor and wait for it to finish
run = client.actor("nabeelbaghoor/email-phone-ip-risk-api").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 '{
  "queries": [
    "user@example.com"
  ]
}' |
apify call nabeelbaghoor/email-phone-ip-risk-api --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,nabeelbaghoor/email-phone-ip-risk-api"
        }
    }
}

```

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/lfkuftmT5MHp6QRit/builds/QBiyfBfrGxx08g4ch/openapi.json
