> ## Documentation Index
> Fetch the complete documentation index at: https://docs.avatcado.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Test Mode

> Test your integration without hitting real upstream services or consuming quota

# Test Mode

Test mode lets you build and test your Avatcado integration without making real VIES/HMRC/BFS/Bronnysund calls or consuming your monthly quota. Use a `avat_test_` API key instead of a `avat_live_` key.

## How it works

* **No upstream calls**: Requests never reach VIES, HMRC, BFS, or Bronnysund
* **No quota usage**: Test requests don't count toward your monthly limit
* **No burst limit**: Test keys are exempt from the per-minute burst limit
* **No rate limit headers**: Since there's no quota or burst limit, rate limit headers are omitted
* **Async endpoints reject test keys**: `/v1/validate/async` and `/v1/validate/async/batch` return `403 forbidden` for `avat_test_` keys. Use a `avat_live_` key for async testing
* **No caching**: Every request returns a fresh response
* **Format validation still applies**: Invalid VAT formats return `invalid_vat_format` just like in live mode
* **`meta.mode: "test"`**: Every test response includes this field so you can distinguish test from live

## Magic VAT numbers

Use these specific VAT numbers to trigger predictable scenarios:

| VAT Number      | Scenario                                | Status | Company                                           |
| --------------- | --------------------------------------- | ------ | ------------------------------------------------- |
| `DE111111111`   | Valid EU company                        | 200    | Test GmbH, Berlin, Germany                        |
| `GB111111111`   | Valid UK company                        | 200    | Test Ltd, London, United Kingdom                  |
| `FR11111111111` | Valid French company                    | 200    | Test SARL, Paris, France                          |
| `DE222222222`   | Valid, no company details               | 200    | `valid: true`, company null                       |
| `DE000000000`   | Invalid VAT                             | 200    | `valid: false`, company null                      |
| `DE999999999`   | Upstream error                          | 503    | `upstream_unavailable`                            |
| `DE888888888`   | Service unavailable                     | 503    | `upstream_unavailable`                            |
| `DE777777777`   | Rate limit exceeded                     | 429    | `rate_limit_exceeded`                             |
| `DE666666666`   | Burst limit exceeded                    | 429    | `burst_limit_exceeded`                            |
| `DE555555555`   | Stale cache fallback                    | 200    | Test GmbH (stale), `source_status: "unavailable"` |
| `CH111111118`   | Valid Swiss company                     | 200    | Test AG, Zurich, Switzerland                      |
| `CH222222225`   | Valid Swiss UID, not VAT-registered     | 200    | `valid: false`, company present                   |
| `LI111111118`   | Valid Liechtenstein company             | 200    | Test Anstalt, Vaduz, Liechtenstein                |
| `NO123456785`   | Valid Norwegian company, MVA-registered | 200    | Test AS, Oslo, Norway                             |
| `NO987654325`   | Valid Norwegian org, not MVA-registered | 200    | `valid: false`, company present                   |
| `CH999999996`   | BFS upstream error                      | 503    | `upstream_unavailable`                            |
| `NO999999999`   | Bronnysund upstream error               | 503    | `upstream_unavailable`                            |

Any other properly formatted VAT number returns `valid: true` with a generic "Test Company" / "Test Address".

## Examples

<CodeGroup>
  ```bash curl theme={null}
  curl -H "Authorization: Bearer avat_test_your_api_key" \
    "https://api.avatcado.com/v1/validate?vat_number=DE111111111"
  ```

  ```typescript @avatcado/node theme={null}
  import Avatcado from "@avatcado/node";

  const avatcado = new Avatcado("avat_test_your_api_key");
  const { data, error } = await avatcado.vat.validate({ vatNumber: "DE111111111" });

  console.log(data?.meta.mode); // "test"
  console.log(data?.data.company.name); // "Test GmbH"
  ```

  ```python Python theme={null}
  from avatcado import Avatcado

  avatcado = Avatcado("avat_test_your_api_key")
  result = avatcado.vat.validate("DE111111111")

  print(result.meta.mode)  # "test"
  print(result.data.company.name)  # "Test GmbH"
  ```
</CodeGroup>

### Valid response

```json theme={null}
{
  "data": {
    "valid": true,
    "vat_number": "DE111111111",
    "country_code": "DE",
    "company": {
      "name": "Test GmbH",
      "address": "Berlin, Germany"
    },
    "requested_at": "2026-03-07T12:00:00Z"
  },
  "meta": {
    "request_id": "550e8400-e29b-41d4-a716-446655440000",
    "request_duration_ms": 2,
    "mode": "test"
  }
}
```

### Error response

```json theme={null}
{
  "error": {
    "code": "upstream_unavailable",
    "message": "Upstream service returned an error",
    "docs_url": "https://docs.avatcado.com/errors/upstream_unavailable"
  },
  "meta": {
    "request_id": "550e8400-e29b-41d4-a716-446655440001",
    "request_duration_ms": 1
  }
}
```

## Behavior notes

* **Consultation numbers** are included for all tiers when a matching `requester_vat_number` is provided
* **Input normalization** works the same as live mode. `"de 111.111.111"` becomes `DE111111111`
* **Non-magic numbers** return a generic valid result, so any integration test with valid-format VAT numbers will succeed
