Every financial-data provider claims accuracy. Here is ours, with the method, the current numbers, and the cases we get wrong — named.
Every SEC XBRL filer, roughly 2009 to today. There is no curated list and no pre-ingested database: a request resolves the company, pulls its filings from SEC EDGAR, normalizes them on the spot and caches the result. If a company has XBRL facts with the SEC, it is in scope — about 10,500 tickers at the time of writing.
Before 2009 is not covered, because XBRL barely existed. That is a real gap against providers advertising 30+ years, and no amount of parsing fixes it — the structured data is not there.
A sweep runs the production normalizer against live SEC data for a sector-stratified set of 39 filers — megacaps, banks, insurers, REITs, utilities, telecoms, ADRs and recent IPOs — chosen because each breaks a different assumption. Every company is checked for:
34 clean · 4 unsupported (reported as such) · 1 known gap — sweep of 39 filers, FY2023
The harness lives in the repository and is run against live SEC data, not fixtures. When it finds something, the finding is fixed and a regression test is pinned to the real numbers.
SAP, Shell, TSMC and Toyota file under IFRS. Their statements do not map onto US-GAAP without
judgement calls, so the API returns a structured UNSUPPORTED_FILER error rather
than a number that looks right and is not. Four of the 39 are in this category. If you need
IFRS coverage, we are not the right tool today.
After a holding-company reorganization, SEC’s ticker file points only at the successor,
whose XBRL history starts at the reorganization. XOM is the live example: it
resolves to the 2024 holding company, so FY2023 Exxon has to be requested as
cik=34088. The error says so and names the years the successor does cover.
Proper successor/predecessor resolution is on the roadmap.
gross_profit is null for banks, insurers, REITs and most telecoms. They have no
cost of revenue, so there is nothing to report — a blank is the honest answer, not a
missing value.
A couple of filers sit under 1% on the balance-sheet identity (rounding and presentation choices inside the filing itself). We treat those as passing and do not paper over them.
Companies revise prior years. Pfizer’s FY2019 revenue was filed as $51.75B in February 2020 and reads $40.9B in the current filings — a 21% difference in the same fiscal year.
By default the API returns the latest reported figure, which is what other sources show.
Pass as_of and you get the value as it was known on that date, with no
look-ahead — the thing a backtest actually needs. And
get_revisions returns the whole series, so you can see when a figure moved
and by how much, with the filing behind each value.
Turn on provenance and each figure carries the SEC accession, the filing date, the form type and a direct EDGAR link. You do not have to trust the normalization — you can open the filing and check it. That is also how to report a problem: tell us the company, the year and the field, and the source link makes it verifiable in a minute.
Open an issue. Normalization edge cases are the most useful feedback this project can get — every fix so far came from one company behaving unlike the rest.