Skip to main content

Enrichment Guide

Turn any domain into 40+ fields of company intelligence — firmographics, social profiles, AI insights, and B2B Match scoring.

Not a developer?

You can enrich companies one-by-one or in bulk from the Dashboard — search a domain, upload a CSV, and export the results. No code required.

Why Async?

Vera uses an asynchronous pattern because high-quality data requires web scraping, AI analysis, and multi-source validation — typically 5-15 seconds per company. You submit a domain, get a job ID, and poll for results. This lets you fire-and-forget or process many companies in parallel.

The Enrichment Flow

┌─────────────┐     ┌─────────────┐     ┌─────────────┐
│ POST │ │ Poll │ │ Get │
│ /enrich │ ──► │ /jobs/{id} │ ──► │ Results │
│ │ │ │ │ │
│ Returns │ │ status: │ │ status: │
│ jobId │ │ processing │ │ completed │
└─────────────┘ └─────────────┘ └─────────────┘

Step 1: Submit Request

POST a domain to /enrich to start a job. See the Quickstart for full request examples. You'll get back a jobId to poll.

The url field accepts any format: stripe.com, www.stripe.com, https://stripe.com/pricing — all normalize to the same domain.

Duplicate requests for the same domain return the existing jobId instead of creating a new job.

Step 2: Poll for Results

Poll /enrich/{id} until the status resolves:

StatusDescription
pendingQueued, waiting to start
processingActively running
completedFinished — data available
failedError occurred
async function enrichCompany(domain) {
const startResponse = await fetch('https://api.veraenrich.com/enrich', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.VERA_API_KEY}`,
'Content-Type': 'application/json'
},
body: JSON.stringify({ url: domain })
});

const { jobId } = await startResponse.json();

for (let i = 0; i < 60; i++) {
const pollResponse = await fetch(
`https://api.veraenrich.com/enrich/${jobId}`,
{ headers: { 'Authorization': `Bearer ${process.env.VERA_API_KEY}` } }
);

const result = await pollResponse.json();

if (result.status === 'completed') return result.data;
if (result.status === 'failed') throw new Error(result.error);

await new Promise(r => setTimeout(r, 1000));
}

throw new Error('Timeout waiting for enrichment');
}

Error Handling

ErrorCauseSolution
AUTHENTICATION_FAILEDInvalid API keyCheck your API key
RATE_LIMIT_EXCEEDEDToo many requestsImplement backoff — see Rate Limits
VALIDATION_ERRORInvalid domainCheck the URL format
JOB_NOT_FOUNDInvalid job IDVerify the jobId from the original response

For production, add exponential backoff on 429 responses. See Rate Limits for retry patterns.

Data Quality

Every enrichment includes a confidence score (0-100) and a sources array:

ScoreQualityDescription
90+HighMultiple sources confirmed
70-89MediumGood data from primary sources
50-69LowLimited data, some inferred
Below 50Very LowUse with caution

See Company Schema for all available fields and Data Sources for how data is collected.

Next Steps