# Spain Company Profile by NIF/CIF: BORME Acts + VIES Check (`sefran1/spain-company-profile`) Actor

Spanish company lookup by NIF/CIF and/or name: CIF checksum and entity type, live EU VIES status with name match, and recent BORME acts (constitution, capital, address, dissolution) with source links. Company-level only. $0.01 per profile.

- **URL**: https://apify.com/sefran1/spain-company-profile.md
- **Developed by:** [Iberia Channel Desk](https://apify.com/sefran1) (community)
- **Categories:** Lead generation, Developer tools
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $10.00 / 1,000 company profiles

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

## Spain Company Profile by NIF/CIF: BORME Acts + VIES Check

Look up Spanish companies by **NIF/CIF and/or company name** and get one clean JSON profile per company:

- **NIF/CIF check**: checksum, entity type (SA, SL, cooperative...), and the province where the CIF was issued. Done offline, so it's instant.
- **EU VIES status**: live check that the NIF is registered for intra-EU VAT. If you give a name, you also get VIES **name match** (VALID / INVALID). Spain doesn't publish names in VIES, so this is the only way to confirm that a NIF belongs to a given company.
- **Recent BORME acts**: constitution, capital increases/reductions, change of registered address, dissolution/extinction, name changes and other corporate acts from the Boletín Oficial del Registro Mercantil (Section A). Each act includes the date, province, registry data and a link to the official BOE page and PDF.
- **CNAE**: given only when the BORME corporate-purpose text states it (common in newer constitutions). Spain has no free official per-company CNAE source, so we never guess it.
- **Sources with dates** on every row.

Built for KYB/onboarding checks, supplier vetting, CRM enrichment and AI agents.

### Input

```json
{
  "companies": ["A28015865 | Telefonica SA", "A46103834", "Banco Santander SA"],
  "bormeDaysBack": 31
}
```

| Form | What you get |
|---|---|
| `NIF \| Name` (recommended) | checksum + VIES + VIES name match + BORME acts |
| `NIF` only | checksum + entity type + VIES status (BORME doesn't publish NIFs, so no acts) |
| `Name` only | BORME acts (all provinces are scanned) |

Other options: `provinces` (add the current registry province if the company moved, e.g. a CIF issued in Barcelona with its seat now in Valencia), `scanAllProvinces`, `checkVies`, `searchBorme`, `bormeTimeBudgetSecs`.

### Output (one item per company)

```json
{
  "status": "ok",
  "legalName": "BANCO SANTANDER, S.A",
  "legalNameSource": "BORME (as published)",
  "nif": "A39000013", "nifValid": true, "entityType": "Sociedad anónima (SA)", "provinceOfIssueHint": "CANTABRIA",
  "vies": { "status": "valid", "vatNumber": "ESA39000013", "nameMatch": "VALID", "checkedAt": "..." },
  "borme": {
    "matched": true, "window": { "from": "2026-09-23", "to": "2026-10-23", "provinces": "ALL" },
    "registryData": "S 8 , H S 1960, I/A 5685 (13.10.26).",
    "latest": { "constitution": null, "capitalChange": null, "addressChange": null, "dissolution": null, "nameChange": null },
    "acts": [ { "date": "2026-10-23", "province": "CANTABRIA", "actTypes": ["Otros conceptos"], "acts": [ { "type": "Otros conceptos", "summary": "Admisión a negociación ..." } ], "sourceUrl": "https://www.boe.es/diario_borme/txt.php?id=BORME-A-2026-205-39" } ]
  },
  "cnae": { "codes": [], "note": "No CNAE code found in the BORME text scanned." },
  "sources": [ "..." ],
  "attribution": "Basado en datos de la Agencia Estatal Boletín Oficial del Estado (https://www.boe.es). ...",
  "charged": true
}
```

`status` is `ok` (charged), `partial` (a source didn't answer or the time budget ran out; not charged), `invalid_input` (bad NIF and no name; not charged) or `skipped_personal_id` (DNI/NIE given; not charged).

### Pricing

Pay per event: **$0.01 per company profile** with `status: ok`. Invalid, partial and personal-ID rows are free. There are no extra per-item charges. You still pay standard Apify platform usage.

### Privacy: company data only

- Input must be a company. Personal DNI/NIE numbers are rejected, and BORME "Empresario Individual" entries are skipped.
- For officer acts (appointments, resignations, revocations, re-elections, auditors, sole-shareholder declarations, powers, errata), only the **act type and date** are returned (`summary: null`).
- For Constitución, only four company fields are returned: comienzo de operaciones, objeto social, domicilio and capital. Everything else in the act is dropped.
- In all other act text, person references are replaced with exactly `[omitted]`. This covers role + name (`Adm. Unico: [omitted]`), honorific + name (D., Dña., Don, Doña, Sr., Sra.), DNI/NIE numbers and any remaining 2–4-word name-like run. As a final guard, a summary that still looks like it contains a person is dropped (`null`).
- Redaction is conservative: some street or activity words may also show as `[omitted]`. Use the BOE link for the full official text.
- You can't search by a person's name.

### Limits (please read)

- BORME is searched over a **rolling window** (default 31 days, max 180), not full history. "No acts" means no acts in that window, not that the company doesn't exist.
- BORME matching is by **exact company name** (legal form and accents are normalised). Give the registered name.
- By default we scan the CIF's province of issue. Companies that moved their registered seat need `provinces` or `scanAllProvinces`.
- VIES is a live EU service that sometimes rate-limits or goes down for maintenance. Affected rows come back `partial` and are not charged. We check each number once per run and stop if VIES blocks us.
- This is not an official registry certificate (nota simple). For legal certainty use the Registro Mercantil.

### Sources and terms

- **BORME** via the BOE open-data API and the BOE act pages, reused under the [BOE aviso legal](https://www.boe.es/informacion/aviso_legal/index.php). *Basado en datos de la Agencia Estatal Boletín Oficial del Estado.* Act text is summarised (person references replaced with `[omitted]`, long text truncated). The only authentic version is the BORME published at boe.es. BOE does not endorse this Actor. Pages and days that BOE excludes in robots.txt are skipped.
- **VIES** is the European Commission's public VAT validation service, used for one check per number.
- The Registro Mercantil / registradores.org (paid, with commercial reuse prohibited) is **not** used.

# Actor input Schema

## `companies` (type: `array`):

One per line: "A28015865 | Telefonica SA" (best), "A28015865" (NIF only: checksum + VIES, no BORME) or "Mercadona SA" (name only: BORME). Company NIFs only; personal DNI/NIE numbers are rejected. Max 500.

## `bormeDaysBack` (type: `integer`):

How many days of BORME Section A to scan for acts. One scan serves the whole batch. 31 = about 1 minute; 180 = several minutes.

## `provinces` (type: `array`):

Registry provinces to scan in BORME, e.g. MADRID, BARCELONA, VALENCIA. By default we scan the province where the CIF was issued; add the current registry province if the company moved.

## `scanAllProvinces` (type: `boolean`):

Scan every province (slower). Automatically on when a company has a name but no valid CIF.

## `checkVies` (type: `boolean`):

Live VAT registration status (and name match when you give a name).

## `searchBorme` (type: `boolean`):

Turn off for a fast NIF + VIES check only.

## `bormeTimeBudgetSecs` (type: `integer`):

Stop scanning older days after this long; affected rows are marked partial and not charged.

## Actor input object example

```json
{
  "companies": [
    "A28015865 | Telefonica SA",
    "A46103834 | Mercadona SA",
    "Banco Santander SA"
  ],
  "bormeDaysBack": 31,
  "scanAllProvinces": false,
  "checkVies": true,
  "searchBorme": true,
  "bormeTimeBudgetSecs": 420
}
```

# Actor output Schema

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

No description

## `summary` (type: `string`):

No description

# 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 = {
    "companies": [
        "A28015865 | Telefonica SA",
        "A46103834 | Mercadona SA",
        "Banco Santander SA"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("sefran1/spain-company-profile").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 = { "companies": [
        "A28015865 | Telefonica SA",
        "A46103834 | Mercadona SA",
        "Banco Santander SA",
    ] }

# Run the Actor and wait for it to finish
run = client.actor("sefran1/spain-company-profile").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 '{
  "companies": [
    "A28015865 | Telefonica SA",
    "A46103834 | Mercadona SA",
    "Banco Santander SA"
  ]
}' |
apify call sefran1/spain-company-profile --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,sefran1/spain-company-profile"
        }
    }
}
```

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/NsgKRAftQWjabLD9w/builds/l8tiK9AsM9fFPBgW5/openapi.json
