DEV Community
Building a Latvian B2B prospect list with turnover and headcount from the open company register (Python)
I built this actor; it's a paid tool on Apify with a free trial credit. Latvia publishes its whole company register as open data. The Register of Enterprises (Uzņēmumu reģistrs, UR) puts every company on data.gov.lv: registration number, name, legal form, status, registration date and legal address. It also publishes the annual reports companies file, so you can see employees, net turnover, net income, total assets and equity for most established firms. In early November 2026 it held 140,324 active limited companies (SIA). The catch is that it comes as separate datasets: the register in one, the financial statements in others, keyed by registration number and report ID. Joining them by hand is fine once. If you want "every SIA in Liepāja with at least 10 staff and a profit last year" every month, you want an API. I'm an 18-year-old engineering student, and I built Latvia Company Register & Financials Scraper to do that join for you. This post covers calling it from Python and Node, what a row looks like, and a small project: a ranked shortlist of established, profitable companies in one town. How it works The actor queries the UR datasets on data.gov.lv over plain HTTP (no browser, no login). It filters the register by town, legal form, name word or registration date, then looks up each company's newest annual report. If a group files both a stand-alone and a consolidated report, it uses the company's own one and tells you which one it is (financials.consolidated). Amounts filed in thousands of euros are scaled to whole euros, so the numbers are comparable across companies. The town filter matches the place parts of the legal address, not the street. Liepāja won't pick up "Rīga, Liepājas iela", which is a common mistake if you just search the address text. Accents are optional. People-run forms (individual merchants, individual and family enterprises) are never output. They're usually named after the owner, and this is a company list. Python example pip install apify-client
from apify_client import ApifyClient
client = ApifyClient("")
run = client.actor("rel8ble/latvia-company-register").call(run_input={
"towns": ["Rīga", "Mārupes nov."],
"companyTypes": ["SIA", "AS"],
"minEmployees": 50,
"includeFinancials": True,
"maxResultsPerSearch": 200,
})
for c in client.dataset(run["defaultDatasetId"]).iterate_items():
print(c["registrationNumber"], "|", c["nameInQuotes"], "|", c["employees"], "staff |",
c["netTurnover"], "EUR |", c["town"])
Companies below minEmployees or minTurnover are read but not saved, so you don't pay for them. Each town is its own search with its own row limit. Node example npm install apify-client
import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: '' });
// New companies: Riga SIA registered since 1 October, newest first
const run = await client.actor('rel8ble/latvia-company-register').call({
towns: ['Rīga'],
companyTypes: ['SIA'],
registeredFrom: '2026-10-01',
sortOrder: 'newest',
includeFinancials: false,
maxResultsPerSearch: 0,
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items.length, 'new Riga companies');
When I ran that on 7 November 2026 it gave 512 companies. New companies have no annual report yet, so turn financials off for this kind of search. Size filters can't work on them either. What a row looks like Real row from the prefilled demo (active SIA in Liepāja, oldest first, 7 November 2026), trimmed: {
"registrationNumber": "42102001645",
"nameInQuotes": "MŪRNIEKS",
"type": "SIA",
"typeEn": "Limited liability company (SIA)",
"register": "Commercial register",
"registered": "1991-04-30",
"status": "active",
"address": "Liepāja, Krūmu iela 11/13",
"postalCode": "LV-3401",
"town": "Liepāja",
"financialYear": 2025,
"employees": 63,
"netTurnover": 2368333,
"netIncom...
Powered by Readybot.io
External Link
Platform
You are about to visit:
https://example.comThis will open in a new tab. Make sure you trust this link.