Freelancer Verification via the KVK API: Check If a Dutch Contractor Is Registered
Working with Dutch freelancers? Use the KVKBase API to verify KVK registration status before paying invoices or starting contracts — automate compliance in minutes.
If your business works with Dutch freelancers (zzp’ers), you have a legal obligation to verify that they are genuinely self-employed. Since 2025, the Dutch Tax Authority (Belastingdienst) has actively enforced the Wet DBA (Deregulation Assessment of Employment Relations Act), meaning that companies using unregistered or incorrectly classified freelancers face back-payments of payroll tax and social security contributions.
The first step in any zzp compliance check is simple: is the freelancer actually registered at the Dutch Chamber of Commerce (KVK)? With the KVKBase API, you can automate this check and integrate it directly into your vendor onboarding flow.
Why KVK Verification Matters for Freelancers
Paying an invoice from someone who is not registered as a business can be reclassified as an employment relationship. The consequences include:
- Back-payment of wage tax (loonbelasting)
- Social security premium assessments
- Potential fines for non-compliance
A verified KVK registration does not by itself prove legal self-employment, but it is a required baseline. Without it, you are already on uncertain legal ground.
What the KVKBase API Returns
For freelancer verification, these are the critical fields:
| Field | Meaning |
|---|---|
naam | Registered business name |
rechtsvorm | Legal form (Eenmanszaak, BV, VOF, etc.) |
actief | Whether the business is currently active |
startdatum | Registration date |
sbiCode | Industry classification |
adres | Current registered address |
A sole trader (rechtsvorm: "Eenmanszaak", actief: true) is the most common structure for Dutch freelancers.
Implementation: Freelancer Verification in Python
import os
import requests
API_KEY=os.env..._URL = "https://api.kvkbase.nl/api/v1"
def verify_freelancer(kvk_number: str) -> dict:
"""
Verify whether a freelancer is actively registered with the KVK.
Raises HTTPError if the KVK number does not exist.
"""
response = requests.get(
f"{BASE_URL}/kvk/{kvk_number}",
headers={"x-api-key": API_KEY},
timeout=10,
)
response.raise_for_status()
data = response.json()
result = {
"kvk_number": kvk_number,
"name": data.get("naam"),
"legal_form": data.get("rechtsvorm"),
"active": data.get("actief", False),
"start_date": data.get("startdatum"),
"sbi_code": data.get("sbiCode"),
"verified": False,
"reason": None,
}
if not result["active"]:
result["reason"] = "Business is no longer registered at the KVK"
return result
if not result["legal_form"]:
result["reason"] = "Legal form unknown"
return result
result["verified"] = True
return result
# Usage
freelancer = verify_freelancer("12345678")
if freelancer["verified"]:
print(f"✓ {freelancer['name']} ({freelancer['legal_form']}) — active registration confirmed")
else:
print(f"✗ Verification failed: {freelancer['reason']}")
Filtering by Legal Form
Not every legal form is equally suitable for freelance work. A sole trader (Eenmanszaak) or private limited company (BV) are the most common. A general partnership (VOF) involves multiple partners, which may require additional scrutiny about who actually performs the work.
ACCEPTED_LEGAL_FORMS = {
"Eenmanszaak",
"Besloten Vennootschap",
"BV",
}
def is_valid_freelancer_form(freelancer: dict) -> bool:
return freelancer["legal_form"] in ACCEPTED_LEGAL_FORMS
Adjust the set based on your own policy. Some companies also accept VOF entities; others prefer to work exclusively with sole traders or BVs.
Integrating Into Your Vendor Onboarding Flow
The check integrates naturally into a new supplier onboarding process:
def onboard_freelancer(name: str, kvk_number: str, email: str) -> str:
"""
Onboard a freelancer after KVK verification.
Returns: 'approved', 'manual_review', or 'rejected'.
"""
try:
data = verify_freelancer(kvk_number)
except requests.HTTPError as e:
if e.response.status_code == 404:
return "rejected" # KVK number does not exist
raise
if not data["verified"]:
log_manual_review(kvk_number, name, data["reason"])
return "manual_review"
if not is_valid_freelancer_form(data):
log_manual_review(kvk_number, name, f"Unusual legal form: {data['legal_form']}")
return "manual_review"
save_freelancer({
"name": data["name"],
"kvk_number": kvk_number,
"legal_form": data["legal_form"],
"email": email,
"verified_at": datetime.utcnow().isoformat(),
})
return "approved"
Periodic Re-certification
A one-time check at onboarding is not enough. Businesses can de-register at any time. Build periodic re-certification into your system for all active freelancers:
from datetime import datetime, timedelta
import time
def recertify_all_freelancers(freelancers: list, max_age_days: int = 90) -> list:
"""
Check all freelancers to see if their KVK registration is still active.
Returns a list of freelancers with issues.
"""
cutoff = datetime.utcnow() - timedelta(days=max_age_days)
flagged = []
for f in freelancers:
last_verified = datetime.fromisoformat(f.get("verified_at", "2000-01-01"))
if last_verified > cutoff:
continue # Recently checked, skip
result = verify_freelancer(f["kvk_number"])
time.sleep(0.2) # Respect rate limits
if not result["verified"]:
flagged.append({
"name": f["name"],
"kvk_number": f["kvk_number"],
"issue": result["reason"],
})
return flagged
# Run daily or weekly
problems = recertify_all_freelancers(get_all_active_freelancers())
for p in problems:
send_alert(f"Freelancer {p['name']} ({p['kvk_number']}): {p['issue']}")
Wet DBA: What Employers Need to Know
The Dutch Tax Authority has been enforcing Wet DBA since 2025. A KVK registration does not guarantee correct labour classification, but it is a mandatory starting point. Combine the KVK check with:
- An approved model agreement (modelovereenkomst)
- Evidence of genuine independence in the work (no fixed workplace, no authority relationship)
- The freelancer working for multiple clients
The KVK verification via the KVKBase API is the technical layer. The legal assessment remains a human judgement call.
Summary
- Verify every new freelancer’s KVK number before starting work or paying invoices
- Check for
actief: trueand an appropriaterechtsvorm - Build periodic re-certification for existing vendors (every 90 days is a sensible interval)
- Automate this as part of your vendor onboarding pipeline
Also read: KVK Data for Customer Onboarding for a broader implementation of KVK verification in your client intake process, and KVK Company Status Monitoring for real-time alerts when registration statuses change.