Open-source Python library
Go deeper with OpenFactsheet for Python.
Build transparent, reproducible performance and risk analysis into research, due diligence, reporting and custom investment workflows.
Private betaThe repository and the reference manual open to everyone at the public release, coming soon. Until then, these links work for invited collaborators only.
- openfactsheet 0.1.0
- Methodology 0.1.0
- Python 3.10 to 3.13
- Apache-2.0
- Typed (mypy --strict)
git clone https://github.com/bagnascotrader/openfactsheet.git
cd openfactsheet
# PyPI release pending: install from source
pip install -e ".[excel]"import openfactsheet as ofs
report = ofs.analyze("fund.csv", benchmark="benchmark.csv")
sharpe = report.metrics["sharpe_ratio"]
print(sharpe.value, sharpe.confidence, sharpe.warnings)
# Benchmark-relative metrics are included
print(report.metrics["beta"].value)
# Self-contained report with SVG charts
report.to_html("fund-factsheet.html")Who it's for
The library is the engine behind every report on this site. Use it wherever you need the same analysis in code.
Developers
Add standardized performance analytics to a product, a pipeline or an internal tool with one function call.
Quantitative researchers
Reproducible results with formula identifiers, a versioned methodology and an input fingerprint on every report.
Investment managers
Report your own track record with every metric shown, including the unflattering ones, under a published methodology.
Allocators and due-diligence teams
Analyze managers' return series the same way every time, with data-quality checks before any figure.
Why a standard matters
A performance figure is only as good as the choices behind it: the period, the frequency, the risk-free rate, the benchmark, what happens to missing months. When everyone makes those choices differently, numbers can't be compared, and a flattering choice is easy to make. One published, versioned standard removes the choice.
- Comparability
- Every manager, fund and mandate measured with the same conventions, chosen in advance. Differences in the numbers are differences in the investments, not in the arithmetic.
- Due diligence
- All metrics, always, with the data checks first: smoothing, stale prices, gaps and outliers are flagged before anyone quotes a ratio.
- Reproducibility
- A SHA-256 fingerprint of the input and a pinned methodology version mean anyone can rerun a report and get the same numbers.
- Audit trail
- Each value carries its formula identifier, methodology version, assumptions, warnings and a link to the page of the reference manual that defines it.
What the library offers
Everything listed here is implemented and tested in openfactsheet 0.1.0.
97 metrics, always all of them
Returns, volatility, drawdowns, risk-adjusted ratios, tail risk, distribution, consistency, serial dependence, benchmark-relative, factor models and statistical confidence. No option to leave one out.
Diagnostics and confidence labels
Missing periods, stale or smoothed returns and outliers are detected and disclosed. Every metric carries a status, a confidence label, warnings and assumptions.
Benchmarks, factors and comparisons
Benchmark-relative metrics when you supply a benchmark. Factor models (CAPM, Fama-French, Carhart or custom) on factor returns you supply. ofs.compare() puts several investments side by side over a common period, never ranked.
Output for people and for code
Deterministic, schema-versioned JSON that never contains NaN; self-contained HTML with SVG charts; Markdown; a terminal report; Python objects and pandas frames.
Flexible input
Lists, NumPy arrays, pandas Series and DataFrames, CSV, wide Year × month tables and pasted table text. Excel needs the excel extra. Price or NAV levels are detected and flagged, never silently converted.
Document ingestion (optional extras)
PDF factsheets with an embedded monthly-return table need the pdf extra; screenshots and scanned PDFs need the ocr extra and run locally. Tables that don't reconcile with their printed YTD are refused.
Quick start
One function does the work. There are deliberately no options for windows, thresholds or metric subsets: the arguments only describe the input, so results from different users are comparable.
With six months of data, as in this example, the library still computes every metric the data allow, labels them low confidence and explains why.
Until the PyPI release, install from source. Add [pdf] or [ocr] to the extras for document ingestion.
import pandas as pd
import openfactsheet as ofs
returns = pd.Series(
[0.01, -0.02, 0.015, 0.005, -0.01, 0.03],
index=pd.date_range("2025-01-31", periods=6, freq="ME"),
)
report = ofs.analyze(returns)
print(report.summary()) # canonical 14-section terminal report
report.to_json("factsheet.json") # deterministic, NaN-free JSON
report.to_html("factsheet.html") # self-contained HTML with charts
report.to_markdown("factsheet.md") # Markdown
report.metrics["sharpe_ratio"] # value, status, confidence, warnings, assumptionsimport openfactsheet as ofs
cmp = ofs.compare({"Fund A": "fund_a.csv", "Fund B": "fund_b.csv"})
print(cmp.table(common_period=True)) # side by side, never rankedThe web tool and the library
The free web tool runs this same library in your browser, and an automated test checks that it produces exactly the numbers native Python does. The library does more, because code can.
| Feature | Free web tool | Python library |
|---|---|---|
| Who it is for | Anyone. No code, no account | Developers, researchers and analysts |
| Methodology and numbers | Methodology 0.1.0 | Methodology 0.1.0, the same code |
| Input | CSV or Excel upload of one return series | Python objects, pandas, CSV, Excel, pasted tables; PDF and OCR with extras |
| Benchmark | Optional file upload | Any supported input |
| Factor models | Not available | Factor returns you supply |
| Compare several investments | One at a time | ofs.compare(), never ranked |
| Output | Quick overview, full factsheet, PDF, JSON and HTML downloads | Python objects, pandas, JSON, HTML, Markdown, terminal |
| Automation | Manual, in your browser | Scripts, notebooks, batch and reproducible research |
Output you can audit
- Deterministic JSON with a versioned schema. Never contains NaN.
- Every metric carries its formula identifier, methodology version, confidence, assumptions and warnings.
- An input fingerprint (SHA-256) makes each report reproducible.
- Every result links to the page of the PDF reference manual that defines it.
{
"schema_version": "0.1",
"methodology": { "version": "0.1.0", ... },
"input": { "observations": 120, "frequency": "monthly", ... },
"data_quality": { "smoothing_risk": "none", "findings": [ ... ] },
"metrics": [
{
"id": "sharpe_ratio",
"value": 0.29542172191685984,
"unit": "ratio",
"status": "applicable",
"confidence": "high",
"formula_id": "sharpe_ratio@v1",
"assumptions": [ "Risk-free rate assumed to be 0% ..." ],
"warnings": []
},
...
]
}Methodology and reproducibility
Methodology 0.1.0 fixes every convention in advance. When a convention changes, the methodology version changes, and old reports stay reproducible.
- No cherry-picking
- Every metric is always computed. The methodology, not the user, picks periods and conventions.
- Diagnose before measuring
- Missing periods, stale or smoothed returns and outliers are detected and disclosed, never silently fixed.
- Cross-validated
- Metrics are checked numerically against R PerformanceAnalytics, empyrical-reloaded, QuantStats and skfolio. Where conventions differ, the difference is documented and pinned by a test.
- Decisions on record
- 35 methodology decision records explain each contested convention, its rationale and its alternatives.
- Risk-free rate of 0%
- Under methodology 0.1.0, Sharpe-type ratios are total-return ratios. Every affected metric states this assumption.
- Local by design
- No network calls and no commercial data. OCR of scanned documents runs locally too.
Report your own track record the fair way
Managers who want to signal transparency can publish an OpenFactsheet report of their own track record: every metric, the data checks, and the methodology version, so investors can rerun it themselves. Showing the full record, unflattering parts included, is a statement in itself.
Cite and contribute
If you use OpenFactsheet in research, please cite it and state the methodology version reported by your results.
Contributions are judged by correctness, transparency and documentation. Changes to a convention go through a decision record and a methodology version bump.
- Contributing guide
- Code of conduct
- Changelog
- Security policy
- Methodology decision records
- Citation file
- License (Apache-2.0)
These files open publicly when the repository does.
@software{openfactsheet,
title = {OpenFactsheet: standardized, transparent investment performance analytics},
author = {{OpenFactsheet contributors}},
version = {0.1.0},
license = {Apache-2.0},
url = {https://github.com/bagnascotrader/openfactsheet}
}