EU VAT Number Validation: Bulk VIES Check & Supplier Monitor
Pricing
from $2.80 / 1,000 vat number checkeds
EU VAT Number Validation: Bulk VIES Check & Supplier Monitor
Validate a whole supplier or customer list against VIES, get the consultation number that proves you checked, and be told the moment a VAT number goes invalid or its registered name changes. Knows the difference between an invalid number and a member state that is simply down.
Pricing
from $2.80 / 1,000 vat number checkeds
Rating
0.0
(0)
Developer
Youssef Farhan
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
5 hours ago
Last modified
Categories
Share
Bulk EU VAT number validation against the official VIES service, with the consultation number that proves you checked, and a memory between runs so you are told the moment a supplier's VAT registration goes invalid or its registered name changes.
Paste a supplier or customer list, get a verdict for every line. Put it on a monthly schedule and it becomes a monitor: from the second run on, it can return only what changed.
The distinction this Actor is built around
VIES answers isValid: false for two completely different things:
- the VAT number is genuinely not registered, and
- the member state's own system did not answer, because it was down, timed out, or refused a concurrent request.
The second case is common. A live sweep of ten member states while building this Actor hit MS_MAX_CONCURRENT_REQ on France on the first attempt. Anything that reads that false at face value tells your finance team that a perfectly good customer's VAT number has gone bad, and your finance team acts on it: they stop zero-rating the invoice, or they freeze the account.
So every check here has three outcomes, never two:
| Verdict | Meaning |
|---|---|
valid | The member state confirmed the number |
invalid | The member state answered, and this number is not registered |
unavailable | The member state did not answer. The number was not re-checked, and the previous verdict is left untouched |
An unavailable result is retried with backoff before it is reported, and it never counts as a change.
Proof that you checked
Supply your own EU VAT number in requesterVatNumber and VIES issues a consultation number with every check, for example WAPIAAAAaDAGUrNE. That reference, with the date, is the evidence a tax authority accepts that you validated the counterparty before zero-rating the invoice. It is stored on every row.
Leave it empty and you still get the verdict, just no reference number to cite.
What you get back
| Field | What it is |
|---|---|
fullVatNumber | Normalised, for example DE811569869 |
validationState | valid, invalid, unavailable, out_of_scope or not_checked |
registeredName / registeredAddress | As held by the member state, where it discloses them |
nameMatch / nameMatchScore | match, mismatch or not_disclosed, against the name you have on file |
consultationNumber | The VIES reference proving the check |
checkedAt | The timestamp VIES returned |
viesResponse | The raw VIES code, for your audit trail |
alerts | Plain-English reasons this line needs attention |
_change | baseline, new, changed, unchanged or not_rechecked |
Coverage
All 27 EU member states, plus XI for Northern Ireland under the Windsor Framework.
Great Britain left VIES with Brexit and is deliberately not covered. A GB number comes back as out_of_scope with an explanation, rather than being quietly reported as invalid, which is what a GB number looks like to anything that just forwards the VIES answer.
How to write your list
One VAT number per line, country code first. Add the name you have on file after a pipe to have it checked too:
IE6388047V | Google Ireland LimitedDE811569869 | Zalando SEIT00488410010 | TIM S.p.A.ES A28017895 | TelefonicaEL094019245
Spaces, dots and dashes are stripped, so you can paste straight out of an ERP export. GR is accepted as a synonym for EL.
Input
| Field | Type | What it does |
|---|---|---|
vatNumbers | array | The numbers to check, one per line |
requesterVatNumber | string | Your own EU VAT number, which unlocks consultation numbers |
nameMatchThreshold | integer | How much of your name must appear in the registered name, as a percentage. Default 60 |
alertsOnly | boolean | Return only the lines that need attention |
onlyChangesSinceLastRun | boolean | Return only what moved. This is what makes it a monitor |
trackChanges | boolean | Keep a baseline between runs. On by default |
watchlistName | string | One history per list, so "suppliers" and "customers" stay separate |
maxVatNumbers | integer | Safety cap per run |
| Alerts | strings | Slack, Discord, Telegram or a webhook, all optional |
Example input
{"vatNumbers": ["IE6388047V | Google Ireland Limited","DE811569869 | Zalando SE","IT00488410010 | TIM S.p.A."],"requesterVatNumber": "EL094019245","onlyChangesSinceLastRun": true,"alertsOnly": true,"watchlistName": "suppliers"}
Example output
{"fullVatNumber": "IE6388047V","validationState": "valid","isValid": true,"registeredName": "GOOGLE IRELAND LIMITED","registeredAddress": "3RD FLOOR, GORDON HOUSE, BARROW STREET, DUBLIN 4","expectedName": "Google Ireland Limited","nameMatch": "match","nameMatchScore": 1.0,"consultationNumber": "WAPIAAAAaDAGUrNE","checkedAt": "2026-09-20T18:34:38.254Z","viesResponse": "VALID","alerts": [],"_change": "unchanged"}
Common questions
How do I validate EU VAT numbers in bulk?
Paste the list into vatNumbers and run. One run handles hundreds of numbers across every member state.
How do I prove to an auditor that I checked a VAT number?
Fill in requesterVatNumber with your own EU VAT number. Every row then carries a VIES consultation number and the timestamp of the check.
Why does the same number say valid one month and unavailable the next?
Because a member state's register was unreachable at that moment. That is reported as unavailable, not as invalid, and your stored verdict from the last good run is left alone.
Why is there no registered name for my German supplier?
Several member states, Germany among them, confirm a number without disclosing the name. Those rows read not_disclosed, which is not a mismatch.
Can it check UK VAT numbers?
Northern Ireland (XI) yes, Great Britain (GB) no. GB left VIES with Brexit and needs HMRC instead.
Does it handle names in Greek or Cyrillic? Validity, yes, always. Name matching compares names in the script they are written in, so a supplier registered in Greek is best left without a name on file rather than matched against a Latin one.
Is an API key needed? No. VIES is a free public service of the European Commission.
Pricing
This Actor is billed per event, plus whatever your Apify plan covers. The events are:
| Event | What triggers it |
|---|---|
| Actor start | Each run starts |
| VAT number checked | Each number VIES returned a real verdict for |
| Notification sent | Each Slack, Discord, Telegram or webhook delivery |
Two things you are deliberately not charged for:
- An
unavailableresult is free. If the member state's register did not answer, you have no verdict, so you are not billed for it. You never pay for VIES being down. - Alerts are free. An invalid number is one you already paid to check, so it is not billed twice.
The current rates are shown on this Actor's Store page. Free-plan runs are capped at a small list so you can see the output shape before subscribing; an Apify plan lifts the cap.
Limits worth knowing
- VIES is a shared public service and rate-limits concurrent requests, so a long list is worked through steadily rather than all at once.
- VIES answers for the member state's register as it stands right now. It has no history, so this Actor builds the history itself by remembering each run.
- Some member states support an official trader-name match. Where they return one it is included; where they do not, the name comparison here is used instead.
- A duplicated VAT number in the list is checked twice and the last row wins for change tracking.
Need something else?
National company registry enrichment, a different export shape, or this wired into your ERP: youssefarhan24@gmail.com