# EU Business Validator: IBAN, VAT, LEI, Sanctions (`facts402/eu-business-validator`) Actor

Bulk-validate IBAN/BIC, EU VAT numbers (live VIES), LEI codes or company names (GLEIF), phone numbers and email addresses, and screen names against the OFAC sanctions lists. One row per item; you pay only for answered items.

- **URL**: https://apify.com/facts402/eu-business-validator.md
- **Developed by:** [Veselin Georgiev](https://apify.com/facts402) (community)
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $10.00 / 1,000 validations

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

## EU Business Validator: IBAN, EU VAT (VIES), LEI, phone, email and OFAC screening

Validate customer and supplier data in bulk before onboarding, invoicing or paying out. Give the Actor a
list of items and get one dataset row per item, ready for Excel, Google Sheets, Make, Zapier, n8n or your
own code. It is built for KYB and onboarding checks, invoice validation, CRM cleanup and AI agents that need
a quick "is this real?" answer.

### What it checks

| Type | What you get |
|---|---|
| `iban` | IBAN structure and checksum, country, bank code and, where the national registry has it, the BIC and bank name |
| `vat` | Offline format check plus a **live** lookup in the EU Commission's VIES service: valid or not, and the registered name and address when the member state publishes them |
| `lei` | A 20-character LEI looked up in GLEIF, or a legal-name search: entity name, status, jurisdiction, registration status |
| `phone` | Parsed and normalised number (E.164), validity, region, number type (mobile, fixed line and so on) |
| `email` | Syntax, domain mail exchangers (live DNS), disposable/throwaway domain flag |
| `sanctions` | Fuzzy name screening against the US OFAC SDN and consolidated (non-SDN) lists, with match scores |

### Input

```json
{
  "items": [
    {"type": "iban", "value": "DE89 3704 0044 0532 0130 00"},
    {"type": "vat", "value": "IE6388047V"},
    {"type": "sanctions", "value": "Banco Nacional de Cuba", "entityType": "entity"}
  ],
  "defaultPhoneRegion": "DE",
  "sanctionsMinScore": 88
}
```

Up to 1,000 items per run. Each row contains your `input`, `ok`, the HTTP `status`, the `result` object (or
an `error`) and `charged`.

### Pricing (pay per event)

| Event | Price | When |
|---|---|---|
| `validation` | $0.01 | one answered IBAN, VAT, phone, email or LEI item |
| `sanctions-screen` | $0.02 | one answered OFAC screen |

You are charged **only** for items that got an answer. Invalid input, temporary errors (for example VIES being
down for a member state) and anything else that is not an answer are free rows with an `error` field. The run
stops cleanly when it reaches the maximum charge you set for the run.

### Data handling and privacy

Emails, phone numbers and IBANs are personal data. The Actor sends each item to the facts402 API over HTTPS,
one request per item, and writes the answer to **your** dataset. facts402 does not store or log request
bodies, and VIES results are passed through per request, not cached or republished.

### Disclaimers

- **Not legal, tax or compliance advice.** Results are automated checks of public sources at the time of the
  request. Confirm important decisions with the authoritative source.
- **Sanctions screening covers OFAC only**, not the EU, UN or UK lists. A fuzzy match is a lead to review, and
  no match is not a clearance. It is not a compliance determination.
- VIES answers on behalf of the member states and is sometimes unavailable. The EU Commission states that the
  service's information must not be retransmitted except as necessary for a legitimate user's activity.
- An IBAN that passes its checksum may still be closed. An email domain with mail exchangers may still reject
  the mailbox.

### Data sources and attribution

- US Treasury OFAC SDN and consolidated sanctions lists (US Government work, public domain).
- GLEIF LEI data (CC0 1.0).
- European Commission VIES VAT number validation service.
- python-stdnum (LGPL-2.1), schwifty (MIT), phonenumbers / libphonenumber (Apache-2.0), email-validator
  (Unlicense) and disposable-email-domains (CC0).

The same checks are available to AI agents pay-per-call over x402 at https://facts402.com.
Questions or a missing check: open an issue on the Actor page.

# Actor input Schema

## `items` (type: `array`):

Up to 1,000 objects per run, each {"type": "iban" | "vat" | "phone" | "email" | "lei" | "sanctions", "value": "..."}. Optional per item: "region" (2-letter country code for phone numbers without a + prefix) and "entityType" (individual, entity, vessel or aircraft, for sanctions). For "lei", a 20-character LEI code is looked up directly; any other value is searched as a legal name.

## `defaultPhoneRegion` (type: `string`):

2-letter country code (e.g. DE) used for phone numbers written without a + prefix. Leave empty to require international format.

## `sanctionsMinScore` (type: `integer`):

Fuzzy-match threshold 70-100 for OFAC screening. Lower finds more possible matches (and more false positives).

## Actor input object example

```json
{
  "items": [
    {
      "type": "iban",
      "value": "DE89 3704 0044 0532 0130 00"
    },
    {
      "type": "vat",
      "value": "IE6388047V"
    },
    {
      "type": "lei",
      "value": "7LTWFZYICNSX8D621K86"
    },
    {
      "type": "phone",
      "value": "+44 20 7946 0018"
    },
    {
      "type": "email",
      "value": "support@github.com"
    },
    {
      "type": "sanctions",
      "value": "Banco Nacional de Cuba"
    }
  ],
  "defaultPhoneRegion": "",
  "sanctionsMinScore": 88
}
```

# Actor output Schema

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

All rows of the default dataset as JSON (answered items and free error rows).

## `overview` (type: `string`):

The default dataset in the Overview view: item, validity, sanctions matches, error.

# 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 = {
    "items": [
        {
            "type": "iban",
            "value": "DE89 3704 0044 0532 0130 00"
        },
        {
            "type": "vat",
            "value": "IE6388047V"
        },
        {
            "type": "lei",
            "value": "7LTWFZYICNSX8D621K86"
        },
        {
            "type": "phone",
            "value": "+44 20 7946 0018"
        },
        {
            "type": "email",
            "value": "support@github.com"
        },
        {
            "type": "sanctions",
            "value": "Banco Nacional de Cuba"
        }
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("facts402/eu-business-validator").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 = { "items": [
        {
            "type": "iban",
            "value": "DE89 3704 0044 0532 0130 00",
        },
        {
            "type": "vat",
            "value": "IE6388047V",
        },
        {
            "type": "lei",
            "value": "7LTWFZYICNSX8D621K86",
        },
        {
            "type": "phone",
            "value": "+44 20 7946 0018",
        },
        {
            "type": "email",
            "value": "support@github.com",
        },
        {
            "type": "sanctions",
            "value": "Banco Nacional de Cuba",
        },
    ] }

# Run the Actor and wait for it to finish
run = client.actor("facts402/eu-business-validator").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 '{
  "items": [
    {
      "type": "iban",
      "value": "DE89 3704 0044 0532 0130 00"
    },
    {
      "type": "vat",
      "value": "IE6388047V"
    },
    {
      "type": "lei",
      "value": "7LTWFZYICNSX8D621K86"
    },
    {
      "type": "phone",
      "value": "+44 20 7946 0018"
    },
    {
      "type": "email",
      "value": "support@github.com"
    },
    {
      "type": "sanctions",
      "value": "Banco Nacional de Cuba"
    }
  ]
}' |
apify call facts402/eu-business-validator --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,facts402/eu-business-validator"
        }
    }
}
```

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/gl0G2dmwF9iAeaZYY/builds/Y8f1akc1nK3Vfa8fL/openapi.json
