← Blog

How to validate email, phone and IP in n8n

n8n has no native Boundstone node yet, so you wire validation through the generic HTTP Request node — here's the exact node config, credential setup, and IF branch.

Contents

You want to validate email in n8n — catch the typos and disposable addresses before they reach your CRM — and you went looking for the Boundstone node. There isn't one yet. A native node is planned, but today you wire Boundstone into n8n the same way you'd wire any REST API that doesn't ship its own node: the built-in HTTP Request node, one credential, and an IF node to act on the answer. It takes about five minutes, and the same pattern validates phone numbers and IP addresses too — you swap the URL and the field name.

What n8n can validate on its own

Before you add an API call, know what you don't need one for. n8n can check email syntax by itself. A Code node with a regex catches empty strings, missing @ signs, and fat-fingered domains without a single network request:

// n8n Code node (Run Once for All Items) — cheap syntax gate, no network
return $input.all().map(item => {
  const email = item.json.email ?? "";
  const looksValid = /^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email);
  return { json: { ...item.json, looksValid } };
});

That regex is free, instant, and often all a form-cleanup step needs. What it can't tell you: whether the domain actually accepts mail, or whether @mailinator.com is a throwaway. For a one-off check you can paste an address into the free email validator — no signup. For validation inside a workflow, that's where the API earns its place: it runs the syntax check and the parts n8n can't.

Configure the HTTP Request node

Add an HTTP Request node after whatever feeds it addresses — a form trigger, a spreadsheet row, a webhook. Set it up:

  • Method: POST
  • URL: https://api.boundstone.io/v1/verify/email
  • Send Body: on → Body Content Type: JSONSpecify Body: Using JSON

The JSON body pulls the email off the incoming item with an expression:

{ "email": "{{ $json.email }}" }

n8n sets Content-Type: application/json for you when the body type is JSON, so you don't add that header by hand.

Store the key in a credential, not the node

Do not type your key into the node. Set Authentication to Generic Credential Type, choose Header Auth, and create a credential with:

  • Name: Authorization
  • Value: Bearer bs_live_YOUR_KEY

n8n encrypts credentials and keeps them out of workflow exports and execution logs. Your bs_live_ key is a server-side secret — n8n runs on the server, so it never reaches a browser, but a credential is still the right home for it. Inline in the node, it leaks the moment you export the workflow or share a screenshot.

Read the response and branch with an IF node

The HTTP Request node parses the response into $json for the next node:

{
  "valid_syntax": true,
  "domain": "example.com",
  "mx_found": true,
  "disposable": false,
  "role_account": false,
  "free_provider": false,
  "checks": {
    "performed": ["syntax", "mx", "disposable_list", "role_list"],
    "not_performed": ["smtp_mailbox", "catch_all"]
  }
}

Add an IF node after it. Use Boolean conditions and set the combinator to OR so any single red flag routes the item to the true output:

  • {{ $json.disposable }} is true
  • {{ $json.mx_found }} is false
  • {{ $json.valid_syntax }} is false

Wire the true output to your reject-or-hold path and the false output to the happy path. Disposable plus no MX record is a strong pair of signals for a signup gate; stacking more of them is the subject of multi-signal signup fraud.

The same node validates phone and IP

Duplicate the node, change the URL and body, and the rest of the pattern holds. The Header Auth credential works for all three endpoints.

For phone numbers, POST to https://api.boundstone.io/v1/verify/phone:

{ "phone": "{{ $json.phone }}" }

It returns valid, e164, country, line_type, and national_format. Branch on {{ $json.valid }} is false.

For IP addresses, POST to https://api.boundstone.io/v1/verify/ip:

{ "ip": "{{ $json.ip }}" }

It returns valid, version, normalized, classification, is_public, and is_bogon. Branch on {{ $json.is_bogon }} is true or {{ $json.is_public }} is false.

Validating a whole spreadsheet at once? POST a raw CSV body to /v1/bulk/email, /v1/bulk/phone, or /v1/bulk/ip and you get back HTTP 202 with a job_id; poll /v1/bulk/:id/results.csv for the finished file. The free tier caps a job at 250 rows, paid at 10,000, and refunds credits for any row that errors.

What "valid" actually means

Every response ends with a checks object, and the half that matters most is not_performed. Read it before you trust a green result.

  • Emailnot_performed is ["smtp_mailbox", "catch_all"]. Boundstone does not open an SMTP connection to the mailbox and does not detect catch-all domains. A "valid" here means the syntax parses, the domain has MX records, and it isn't on the disposable or role lists — not that a human reads that inbox.
  • Phonenot_performed is ["carrier_lookup", "ported_status", "hlr_liveness"]. No carrier lookup, no ported-status check, no HLR liveness ping by default. Those run as a paid opt-in with hlr:true, at 5 credits, refunded when the network cannot answer.
  • IPnot_performed is ["geolocation", "asn", "hosting_datacenter", "proxy_vpn_tor", "reputation"]. No geolocation, no ASN, no datacenter or VPN/proxy/Tor detection, no reputation score. That layer needs licensed data Boundstone doesn't ship today.

The not_performed list isn't fine print — it's the point. It tells you exactly what a "valid" did and didn't cover, so you never mistake "well-formed" for "reachable." The full field reference lives in the docs.

The short version

  • No native Boundstone node yet — one is planned. Use the built-in HTTP Request node.
  • POST to https://api.boundstone.io/v1/verify/email with body {"email": "{{ $json.email }}"}.
  • Store the key in a Header Auth credential (Authorization / Bearer bs_live_...), never inline in the node.
  • Add an IF node and branch on disposable, mx_found, or valid_syntax.
  • Swap the URL for /v1/verify/phone or /v1/verify/ip; the same credential covers all three.
  • Read checks.not_performed on every response so you know what a "valid" didn't check.

Frequently asked questions

How do I validate email, phone, and IP addresses inside an n8n workflow?

There is no dedicated Boundstone node in n8n, so you call the REST API from n8n's generic HTTP Request node. Point it at POST /v1/verify/email, /v1/verify/phone, or /v1/verify/ip, pass your API key as a bearer token, and map the field you want to check from the previous node. Every response includes a checks.performed and checks.not_performed list, so your workflow always knows exactly what was verified. The free tier gives 250 credits per month with no card required and credits that never expire.

What does a 'valid' email or phone result in n8n actually confirm?

For email, valid means the syntax is correct, the domain has MX records, and the address is not on our disposable-domain or role-account lists; it does not prove a mailbox exists or that mail will be delivered, because SMTP mailbox and catch-all checks are not performed. For phone, valid confirms the format, region, and line-type metadata, but not that the number is currently active or reachable, since carrier lookup, ported-status, and HLR liveness are not performed. That transparency is the point: each response spells out in checks.not_performed exactly what the result does and does not prove, so you can build your n8n logic on facts rather than assumptions.

Can I validate a whole list of contacts in n8n instead of one record at a time?

Yes. Rather than looping one API call per row, you can POST a CSV to the bulk endpoints at /v1/bulk/email, /v1/bulk/phone, or /v1/bulk/ip. Free accounts process up to 250 rows per job and paid accounts up to 10,000, with credits reserved per row and automatically refunded for any row that errors. This lets an n8n workflow submit a batch, then retrieve the results as a CSV once the job completes.

Thomas Tsui

Founder of Boundstone — building phone, email and IP validation you can actually verify.

One honest API for email, phone and IP — every response lists what it checked and what it didn't claim to. Free tier: 250 credits/month, no card, credits never expire.

More from Boundstone — API documentation · Benchmark methodology · The benchmark series · Buyer's checklist