Portfolio LabBeta

Fundamental backtest: methodology for metrics from annual reports

Advanced9 min read · updated 7 November 2026 · 3 sources

The fundamental backtest selects US stocks at each date by up to ten metrics from annual reports and carries the portfolio forward to today. This methodology describes what the code behind the fundamental backtest page does: where the numbers come from, when they apply, how selection, weights, fallback and costs work, and where the limits are.

Universe and data

The universe consists of the US companies listed on NYSE, Nasdaq or Cboe today, according to the SEC ticker list, with one ticker per company. Only companies that file an annual report on Form 10-K are included; foreign issuers filing 20-F or 40-F are missing. Figures come from the SEC's XBRL data per company (US GAAP, US dollars):

  • Annual reports: Forms 10-K and 10-KT (transition period after a change of fiscal year), without amendments 10-K/A. For each report, the values count as they stood in exactly that report, together with the filing date. Later corrections appear in later reports with their own date.
  • Fiscal year: the reporting date is the latest end of a period of 330 to 400 days for revenue, net income, operating income or operating cash flow; prior-year values (reporting date 345 to 385 days earlier) come from the same report.
  • Share count: from the cover page of annual and quarterly reports (several share classes combined) with the filing date; if missing, the diluted weighted average share count of the annual report.
  • Prices: closing price on the last trading day of each month, once adjusted only for splits (for market cap) and once with dividends reinvested (for returns).

The nightly run refreshes each company's reports every 20 days and the prices after each month-end. XBRL data exist for large companies from mid-2009 and for all from mid-2011. A test therefore starts in June 2010 at the earliest and in June 2012 by default.

No look-ahead: which figures apply at a date

Dates are month-ends. At a date D, each company's annual report filed most recently before D counts; a report filed on D itself only counts at the next date, because it may have arrived after the close. If the reporting date of that report lies more than 18 months before D, the company drops out at that date. The rule thus sees only what was public at the time, and no later corrected figures.

EventDateConsequence
End of fiscal year 202412/31/2024nothing yet
Annual report filed02/28/2025not yet used at the 02/28/2025 date
First date with the figures03/31/2025metrics from the 2024 report
Last possible date without a new report06/30/2026reporting date plus 18 months

Market cap at the date is the split-adjusted closing price times the share count of the last cover page before D, converted across all splits after the cover page's date. This is the same value as the price at the time times the share count at the time:

closing price at the date in today's share count
share count from the cover page as of t, filed before D
product of split ratios after t (2 for a 2:1 split)

Metrics

All metrics come from the valid annual report and the market cap at the date. If a value is missing or the denominator is not positive, the metric is missing, and a criterion on it counts as not met. A P/E thus exists only with a profit, a P/B only with positive equity.

MetricCalculation
P/E, P/B, P/Smarket cap / net income, equity or revenue
Price/free cash flowmarket cap / (operating cash flow − capital expenditure)
EV/EBITDA(market cap + financial debt − cash) / (operating income + depreciation and amortization)
Earnings yield, dividend yieldnet income or dividends paid / market cap
Return on equitynet income / average equity of the prior year and the year
Marginsgross profit (if missing: revenue − cost of revenue), operating income, net income, free cash flow / revenue
Growthrevenue, earnings per share and diluted share count versus the prior year
Debt/equityfinancial debt in % of equity; 0 if no debt is reported
Momentum 12-1return with dividends from 12 months to 1 month before the date
Volatility 12 Mstandard deviation of the last 12 monthly returns × √12

Monthly returns above five times or below one fifth that almost fully reverse in the following month (product of both months between 0.5 and 2) count as errors in the price data and are set to 0 in both months.

Selection, weights and fallback

The universe at a date contains all companies with a valid report, a price and a market cap from the minimum (default $1,000 million); optionally without banks, lenders, insurers, exchanges, brokers and asset managers. Hits are the stocks that meet all criteria (up to 10, each ≥ or ≤). With a maximum, the code takes the first by a chosen metric, otherwise by market cap. Weights are equal or by market cap.

For the case that too few or no stocks remain, there is a minimum number m (default 10) and a fallback:

number of hits at the date
minimum number, 1 to 100
money market (3-month US Treasury bills), the S&P 500 with dividends or the equal-weighted universe

Rebalancing, drift and costs

Rebalancing is monthly, quarterly (end of March, June, September, December) or annually at the end of June, at the closing price on the date. By the end of June, the annual reports of most companies with a December fiscal year are long available; Fama and French also form their portfolios at mid-year with the prior year's financial statements so that the figures are surely known (Fama and French 1993). Between dates, weights drift with prices. If a monthly return is missing for a stock held, it counts as 0.

weight at the start of the month (drifted) and monthly return with dividends per stock
share and monthly return of the fallback
trading costs per traded share, default 10 basis points (0 to 200)
arise at the date and reduce the return of the first month after it

Comparison and metrics of the result

The strategy stands next to two comparisons: the S&P 500 (ETF with dividends reinvested) and the equal-weighted universe, in the same rhythm and without costs. The universe has the same selection of companies listed today. The gap between the strategy and the universe therefore shows what the criteria contribute better than the gap to the S&P 500. Metrics as in the backtest: return p.a., volatility, max. drawdown, Sharpe and Sortino with the money market as the risk-free rate, beta and alpha versus the S&P 500. Plus, per date: universe, hits, stocks held, share in the fallback and turnover, the sectors per year and how much each criterion filters out.

Limits

  • Survivorship bias: companies that were taken over, went bankrupt or delisted since the start are missing from the universe, along with their last, often large losses (Shumway 1997; Brown et al. 1992). This flatters above all rules that buy cheap, small or highly indebted stocks.
  • Early years: until mid-2012 mostly large companies have data; the universe is then smaller and consists almost only of large companies.
  • Data quality: companies label line items differently in XBRL; the code uses a fixed list of common tags per item. If an item is missing, the metric is missing.
  • Today's classification: sectors and tickers are as of today.
  • Trading: at the closing price on the date, without taxes, market impact and securities lending; no short sales.

Frequently asked questions

When may a backtest use a figure from an annual report?

Only after it has been filed with the SEC. At each month-end, the fundamental backtest uses only reports filed before, with the values as they stood in the report at the time. Later corrections only count from their own filing date.

What happens if no company meets all criteria?

Then the entire portfolio sits in the fallback until the next date: money market, S&P 500 or the equal-weighted universe. With fewer hits than the minimum number, each stock gets the share it would have at the minimum number, and the rest goes into the fallback.

Why is the result too good?

Because the universe consists of the companies listed today. Companies that went bankrupt or were taken over in between are missing (survivorship bias). So compare the rule with the equal-weighted universe, which has the same flaw.

Why is a stock missing although it meets the criteria today?

Common reasons: the annual report is older than 18 months, a required figure is missing in the XBRL data, the market cap is below the minimum, or the company does not file a report on Form 10-K (foreign issuers).

Which rebalancing suits annual reports?

Annually at the end of June uses the reports once almost all are available, with little turnover. Monthly and quarterly rebalancing brings new reports into the portfolio faster but costs more trading, especially since the metrics change with the price every month.

Literature

  1. Brown, Stephen J.; Goetzmann, William; Ibbotson, Roger G.; Ross, Stephen A. (1992): Survivorship Bias in Performance Studies. Review of Financial Studies 5 (4), pp. 553–580. doi:10.1093/rfs/5.4.553
  2. Fama, Eugene F.; French, Kenneth R. (1993): Common risk factors in the returns on stocks and bonds. Journal of Financial Economics 33 (1), pp. 3–56. doi:10.1016/0304-405x(93)90023-5
  3. Shumway, Tyler (1997): The Delisting Bias in CRSP Data. The Journal of Finance 52 (1), pp. 327–340. doi:10.1111/j.1540-6261.1997.tb03818.x

Full bibliography

This page describes how Portfolio Lab calculates; past results are not a forecast. All terms in the glossary.