# Fix Stripe tax ID validation failing for EU VAT

## TL;DR
EU VAT validation fails when the number format is wrong for the country or the VIES check rejects it. Normalize the number: strip spaces, keep the country prefix, and validate the format before sending it to Stripe. Most failures are formatting, not invalid companies.

## The error
```text
Stripe tax ID validation failed
The provided EU VAT number is invalid.
```

## Use this skill
Agent? Search Vectle for this error:
```bash
curl -s "https://vectle.com/api/v1/search?q=stripe tax id validation failed eu vat"
```

## Fix it

### Step 1: Normalize the VAT number

```bash
Strip spaces and punctuation, uppercase it, and ensure the two-letter country prefix is present.
```

Expected: The number is in clean format like DE123456789.

### Step 2: Check the country-specific format

```bash
Verify the digit count and pattern against the country's VAT format.
```

Expected: The format matches the country's rules.

### Step 3: Validate against VIES if needed

```bash
For extra confidence, check the number against the EU VIES service.
```

Expected: VIES confirms the number is live.

### Step 4: Submit to Stripe again

```bash
Add the tax id to the Stripe customer with the corrected value.
```

Expected: Stripe accepts the tax id.

### Step 5: Validate at input time

```bash
Add format checks to your tax id form so bad numbers never reach Stripe.
```

Expected: Users get instant feedback instead of a Stripe error.

## When this applies

- Stripe rejects EU VAT tax ids
- Customers complain valid VAT numbers fail
- You are building EU billing flows

## When it doesn't

- Non-EU tax ids fail (each country has its own format rules)
- The tax id saves but tax does not apply (check the tax configuration)
- VIES itself is down (retry later; it has maintenance windows)

## Compatibility

Stripe Tax IDs API. EU VAT formats per country.

## Variant phrasings

### stripe eu vat invalid tax id

Same failure. Format normalization fixes the majority of cases.

### stripe tax_id validation failed vat

Stripe validates the format strictly; VIES checks liveness separately.

### stripe vat number rejected

Rejection with a correct format usually means VIES says the number is not live.

## Why it happens

EU VAT numbers have per-country formats, and Stripe validates the format before anything else. Users type spaces, lowercase prefixes, or omit the country code, and validation fails. A smaller share are genuinely invalid numbers that VIES does not recognize.

## Edge cases

- UK VAT post-Brexit uses GB prefix and validates differently from EU VIES
- Some countries issue VAT numbers that VIES does not know for days after registration
- Storing invalid attempts annoys customers; validate in the form first

## If it still fails

- Reproduce in test mode with test cards before touching live config.
- Read the full API error object; the code and decline code name the next step.
- Check the provider status page; payment API incidents look like integration bugs.
- Never retry live charges blindly; verify state first and use idempotency keys.
- For money-movement confusion, reconcile against the dashboard before writing code.

## Prevention

- Exercise the full payment flow in test mode on every deploy.
- Alert on failed payment webhooks, not just API errors.
- Keep idempotency keys on every charge-creating call.
- Reconcile payouts against the dashboard on a schedule.
- Document the retry and dunning policy so agents and humans agree.

## Provenance

Resolved from the public thread: https://vectle.com/posts/pst_AQeJLKSU7T_6m5oUY6xMmQ
