Skip the 12-vendor leaderboards, including ours: we have not published one, and a public score cannot tell you how a vendor does on your market. Run a blind test on 100 contacts you can verify. This guide shows the method with LeadOcean as the first vendor and one scoring sheet that works for any other.
TL;DR
- Build a list of 100 people you can verify, run each vendor on it, and score hit rate, email status and phone coverage. Plan on about 90 minutes.
- On LeadOcean the test spends at most 100 of your 1,000 free records. Misses are free 404s, and every sizing count is free.
- Repeat the same script per vendor and compare on your list. Do not compare vendor totals.
Prerequisites
- A free LeadOcean key from app.leadocean.io, exported as
$LEADOCEAN_API_KEY. No card. - A free or trial account at each vendor you want to test, with their API key in its own variable.
- 100 contacts with LinkedIn URLs, taken from your CRM and closed-won deals. Not scraped from a vendor.
curl,jqand a spreadsheet.
Step 1: Size your market before you test anything
Start with a free count so you know whether the vendor holds your segment at all. A count spends no records, however often you run it.
curl -s "https://api.leadocean.io/v1/people/search?count=true" \
-H "x-api-key: $LEADOCEAN_API_KEY" \
-H "Content-Type: application/json" \
-d '{"jobLevel":["VP"],"jobFunction":["Sales & Business Development"],"country":["DE"],"limit":1}'count=true goes in the query string, not the body. The response has meta.total (capped at 100,000) and an empty data array.
Step 2: Build the test list
Take 100 rows with one LinkedIn URL each. Mix 70 current customers or known leads with 30 hard cases: small firms, non-US contacts, people who changed jobs lately. Hard cases are where vendors differ.
linkedin_url,known_title,known_company,known_country
https://www.linkedin.com/in/jane-doe-example,VP Sales,Acme,DEWrite the truth you already know in the other columns. You will score each vendor against it.
Step 3: Run LeadOcean on the list
Enrich takes exactly one of linkedin_url, email, phone or person_id. Free keys run 5 requests a second, so pace the loop.
mkdir -p out
tail -n +2 list.csv | cut -d, -f1 | while read url; do
id=$(echo "$url" | md5)
curl -s -o "out/$id.json" -w "%{http_code}\n" -X POST "https://api.leadocean.io/v1/people/enrich" \
-H "x-api-key: $LEADOCEAN_API_KEY" \
-H "Content-Type: application/json" \
-d "{\"linkedin_url\":\"$url\",\"reveal_email\":true}" > "out/$id.code"
sleep 0.25
doneOn Linux use md5sum | cut -c1-12 instead of md5. A 404 means we hold nobody for that URL and it costs nothing. A 200 costs one record.
Step 4: Score every vendor the same way
Count a hit only when the returned title and company match your truth column. A profile returned for the wrong person is a miss, not a hit.
for c in out/*.code; do
if [ "$(cat "$c")" = "200" ]; then
jq -r '.data.contact_data | [.contact_current_experiences[0].job_title,
.contact_current_experiences[0].company_name,
.email_status, ((.contact_phones // []) | length > 0)] | @tsv' "${c%.code}.json"
fi
done | tee hits.tsv
wc -l hits.tsvPut these columns in the sheet for each vendor:
| Metric | How to count it |
|---|---|
| Hit rate | Matched people divided by 100 |
| Title match | Title agrees with your truth column |
| Email present | An address came back |
| Email status | Share marked verified, not just present |
| Phone present | At least one number came back |
| Cost per hit | Plan price or credits spent, divided by hits |
LeadOcean returns an email status with each address, among them verified, catch_all_valid, catch_all, risky and invalid. Ask every other vendor for the equivalent and score it the same. If a vendor gives no status, treat every address as unverified.
Step 5: Send a sample of emails through a checker
Presence is not accuracy. Take 30 addresses per vendor and run them through one independent verifier, then compare bounce rates. This is the only step that tells you whether the data works.
for c in out/*.code; do
[ "$(cat "$c")" = "200" ] && jq -r '.data.contact_data.contact_emails[0].email // empty' "${c%.code}.json"
done | head -30 > sample_emails.txt
wc -l sample_emails.txtAddresses sit in contact_data.contact_emails[], best first, each with its own email, type and status (enrich docs).
Use the checker you already pay for. Run the identical file for each vendor on the same day, because deliverability drifts.
Step 6: Price the winner at your real volume
Cost per hit depends on volume and on whether misses are billed. Read each vendor's pricing page on the day you test, and note whether a lookup that finds nothing is charged.
LeadOcean has no credits on paid plans: Solo is $97 a month, Agency is $497 a month and Platform is $1,997 a month, each with a fair-use pace. Free is 1,000 records for life. A search page of 25 is 25 records, and an enrichment that finds nothing costs none.
For a vendor with credits, multiply only a rate you can read on the page. If the page shows no price at your volume, record "No public price at volume" rather than extrapolating.
Step 7: Read the results with a rule set
Decide your pass marks before you look at the numbers. Otherwise the vendor you already like wins.
- Set a minimum hit rate on your 70 core contacts before you start, and judge the 30 hard cases separately.
- Rank vendors on verified-email share first. A high hit rate with unverified addresses means bounces.
- Reject any vendor whose wrong-person rate is above a few percent. A confident wrong profile costs more than a miss.
- Rerun the winner and the runner-up with a second, fresh list of 100 a week later. If the order flips, the gap is noise.
Keep the sheet. Rerun the same 100 contacts every quarter, since vendors change their data and their pricing.
What you get
The sizing call from Step 1, run through the free leadocean_count_leads MCP tool on 2026-10-21:
{
"filters": {"jobLevel": ["VP"], "jobFunction": ["Sales & Business Development"], "country": ["DE"]},
"total": 1395,
"totalIsExact": true,
"totalAll": 3893,
"distinctCompanies": 905,
"credits": 0
}The total of 1,395 counts only people whose best email is verified, catch_all_valid or catch_all. Without an email condition the same filters match 3,893. That gap is the first number to compare across vendors.
The enrich response carries the current role in contact_data.contact_current_experiences[], addresses in contact_data.contact_emails[], phones in contact_data.contact_phones[].phone, and career history in resume_data when held. Response shape from the API reference, with placeholder values:
{
"success": true,
"data": {
"contact_data": {
"email_status": "verified",
"contact_emails": [{"email": "jane.doe@acme.com", "type": "work", "status": "verified"}],
"contact_phones": [{"phone": "+1 415 555 0133", "type": "mobile"}],
"contact_current_experiences": [{"job_title": "VP Sales", "company_name": "Acme"}]
},
"resume_data": {"experiences": [], "educations": []}
}
}Troubleshooting
| Error | Cause | Fix |
|---|---|---|
| 401 | Missing or wrong x-api-key | Check $LEADOCEAN_API_KEY is exported in this shell |
| 429 | Above your plan's rate limit (5 a second on Free, 200 on Agency) | Honor Retry-After and keep the 0.25 second sleep |
| 402 | Your records are spent | Check GET /v1/usage, then move to a paid plan |
| 404 on enrich | We hold nobody for that LinkedIn URL | Free. Count it as a miss and move on |
| Empty search results | A filter value is not an exact enum string | List values with GET /v1/enums or leadocean_list_enum_values |
| Export refused | Over 50,000 rows a request or 500,000 a day | Split the export; bulk CSV is not on Free |
FAQ
Why not publish a 12-vendor benchmark?
Because the result depends on your segment. A vendor strong in US SaaS can be weak in Germany. A public table also goes stale within a month, and nobody can check our list.
How many contacts do I need?
100 shows large gaps, and 300 narrows the noise. At 50, one odd row moves the hit rate by two points.
Can I run the test through an AI agent?
Yes. LeadOcean's hosted MCP server at https://api.leadocean.io/mcp has 13 tools, and counts, filter lists and enum lookups are free. Search and enrichment tools spend records, so keep the 100-row cap in your prompt.
Does the free plan cover the whole test?
Yes, if you stay within 100 enrichments. Free has 1,000 records for life, every feature, 5 requests a second and one key.
Related reading: what data enrichment is, what it actually costs, a CLI for enrichment and LeadOcean pricing.
Test enrichment on your own list before you pay for it
Free to start. No credit card. 1,000 records to spend whenever you like.
Get your free API key →