ATverify

registry_unavailable

The upstream registry (VIES, HMRC, BFS, or Brønnøysund) returned an error or is temporarily down.

HTTP 502 · Bad Gateway

Example response

{
  "error": {
    "code": "registry_unavailable",
    "message": "VIES fault: MS_MAX_CONCURRENT_REQ"
  },
  "meta": {
    "request_id": "a1b2c3d4-...",
    "latency_ms": 1840
  }
}

What happened

The upstream registry returned an error, timed out, or is temporarily unavailable. This is not a problem with your request. It is a transient failure at the registry level. VIES in particular is prone to throttling errors (MS_MAX_CONCURRENT_REQ, MS_UNAVAILABLE) during peak hours.

Check meta.source in the response to see which registry failed (vies, hmrc, bfs, or brreg).

How to fix

Implement retry logic with exponential backoff:

// Retry 502 with backoff: 250ms → 500ms → 1s
const delays = [250, 500, 1000];
let result;
for (let i = 0; i <= delays.length; i++) {
  try {
    result = await client.validate({ vat_number });
    break;
  } catch (err) {
    if (err instanceof RegistryError && i < delays.length) {
      await new Promise(r => setTimeout(r, delays[i]));
    } else {
      throw err;
    }
  }
}

The @vatverify/node SDK handles this automatically with max_retries: 2 by default.

Common mistakes

  • Treating 502 as a permanent failure: registry outages are temporary. Always retry before surfacing an error to the user.
  • Retrying with no backoff: immediate retries under load can worsen throttling. Use backoff.
  • Not checking meta.source_status: "degraded": when source_status is degraded, we returned a cached result despite the registry being down. The response is still useful. The valid value is from a recent real lookup.
  • Missing per-item 502s in batch responses: in batch calls, a registry_unavailable per-item error means that specific number failed. The rest of the batch may still have succeeded. Always iterate results and handle ok: false items.
  • rate_limited: quota exhausted (your side, not the registry)