Consolidate metric definitions with Rust JSON as single source of truth

- Add core.computed.json with 32 ratio definitions (filing + market derived)
- Add Rust types for ComputedDefinition and ComputationSpec
- Create generate-taxonomy.ts to generate TypeScript from Rust JSON
- Generate lib/generated/ (gitignored) with surfaces, computed, kpis
- Update financial-metrics.ts to use generated definitions
- Add build-time generation via 'bun run generate'
- Add taxonomy architecture documentation

Two-phase ratio computation:
- Filing-derived: margins, returns, per-share, growth (Rust computes)
- Market-derived: valuation ratios (TypeScript computes with price data)

All 32 ratios defined in core.computed.json:
- Margins: gross, operating, ebitda, net, fcf
- Returns: roa, roe, roic, roce
- Financial health: debt_to_equity, net_debt_to_ebitda, cash_to_debt, current_ratio
- Per-share: revenue, fcf, book_value
- Growth: yoy metrics + 3y/5y cagr
- Valuation: market_cap, ev, p/e, p/fcf, p/b, ev/sales, ev/ebitda, ev/fcf
This commit is contained in:
2026-03-15 15:22:51 -04:00
parent ed4420b8db
commit 24aa8e33d4
11 changed files with 1453 additions and 123 deletions

View File

@@ -0,0 +1,389 @@
{
"version": "fiscal-v1",
"pack": "core",
"computed": [
{
"key": "gross_margin",
"label": "Gross Margin",
"category": "margins",
"order": 10,
"unit": "percent",
"computation": {
"type": "ratio",
"numerator": "gross_profit",
"denominator": "revenue"
}
},
{
"key": "operating_margin",
"label": "Operating Margin",
"category": "margins",
"order": 20,
"unit": "percent",
"computation": {
"type": "ratio",
"numerator": "operating_income",
"denominator": "revenue"
}
},
{
"key": "ebitda_margin",
"label": "EBITDA Margin",
"category": "margins",
"order": 30,
"unit": "percent",
"computation": {
"type": "ratio",
"numerator": "ebitda",
"denominator": "revenue"
}
},
{
"key": "net_margin",
"label": "Net Margin",
"category": "margins",
"order": 40,
"unit": "percent",
"computation": {
"type": "ratio",
"numerator": "net_income",
"denominator": "revenue"
}
},
{
"key": "fcf_margin",
"label": "FCF Margin",
"category": "margins",
"order": 50,
"unit": "percent",
"computation": {
"type": "ratio",
"numerator": "free_cash_flow",
"denominator": "revenue"
}
},
{
"key": "roa",
"label": "ROA",
"category": "returns",
"order": 60,
"unit": "percent",
"computation": {
"type": "simple",
"formula": "net_income / average(total_assets)"
}
},
{
"key": "roe",
"label": "ROE",
"category": "returns",
"order": 70,
"unit": "percent",
"computation": {
"type": "simple",
"formula": "net_income / average(total_equity)"
}
},
{
"key": "roic",
"label": "ROIC",
"category": "returns",
"order": 80,
"unit": "percent",
"computation": {
"type": "simple",
"formula": "nopat / average_invested_capital"
}
},
{
"key": "roce",
"label": "ROCE",
"category": "returns",
"order": 90,
"unit": "percent",
"computation": {
"type": "simple",
"formula": "operating_income / average_capital_employed"
}
},
{
"key": "debt_to_equity",
"label": "Debt to Equity",
"category": "financial_health",
"order": 100,
"unit": "ratio",
"computation": {
"type": "ratio",
"numerator": "total_debt",
"denominator": "total_equity"
}
},
{
"key": "net_debt_to_ebitda",
"label": "Net Debt to EBITDA",
"category": "financial_health",
"order": 110,
"unit": "ratio",
"computation": {
"type": "simple",
"formula": "net_debt / ebitda"
}
},
{
"key": "cash_to_debt",
"label": "Cash to Debt",
"category": "financial_health",
"order": 120,
"unit": "ratio",
"computation": {
"type": "simple",
"formula": "(cash_and_equivalents + short_term_investments) / total_debt"
}
},
{
"key": "current_ratio",
"label": "Current Ratio",
"category": "financial_health",
"order": 130,
"unit": "ratio",
"computation": {
"type": "ratio",
"numerator": "current_assets",
"denominator": "current_liabilities"
}
},
{
"key": "revenue_per_share",
"label": "Revenue per Share",
"category": "per_share",
"order": 140,
"unit": "currency",
"computation": {
"type": "per_share",
"source": "revenue",
"shares_key": "diluted_shares"
}
},
{
"key": "fcf_per_share",
"label": "FCF per Share",
"category": "per_share",
"order": 150,
"unit": "currency",
"computation": {
"type": "per_share",
"source": "free_cash_flow",
"shares_key": "diluted_shares"
}
},
{
"key": "book_value_per_share",
"label": "Book Value per Share",
"category": "per_share",
"order": 160,
"unit": "currency",
"computation": {
"type": "per_share",
"source": "total_equity",
"shares_key": "diluted_shares"
}
},
{
"key": "revenue_yoy",
"label": "Revenue YoY",
"category": "growth",
"order": 170,
"unit": "percent",
"computation": {
"type": "yoy_growth",
"source": "revenue"
}
},
{
"key": "net_income_yoy",
"label": "Net Income YoY",
"category": "growth",
"order": 180,
"unit": "percent",
"computation": {
"type": "yoy_growth",
"source": "net_income"
}
},
{
"key": "eps_yoy",
"label": "EPS YoY",
"category": "growth",
"order": 190,
"unit": "percent",
"computation": {
"type": "yoy_growth",
"source": "diluted_eps"
}
},
{
"key": "fcf_yoy",
"label": "FCF YoY",
"category": "growth",
"order": 200,
"unit": "percent",
"computation": {
"type": "yoy_growth",
"source": "free_cash_flow"
}
},
{
"key": "3y_revenue_cagr",
"label": "3Y Revenue CAGR",
"category": "growth",
"order": 210,
"unit": "percent",
"computation": {
"type": "cagr",
"source": "revenue",
"years": 3
},
"supported_cadences": ["annual"]
},
{
"key": "5y_revenue_cagr",
"label": "5Y Revenue CAGR",
"category": "growth",
"order": 220,
"unit": "percent",
"computation": {
"type": "cagr",
"source": "revenue",
"years": 5
},
"supported_cadences": ["annual"]
},
{
"key": "3y_eps_cagr",
"label": "3Y EPS CAGR",
"category": "growth",
"order": 230,
"unit": "percent",
"computation": {
"type": "cagr",
"source": "diluted_eps",
"years": 3
},
"supported_cadences": ["annual"]
},
{
"key": "5y_eps_cagr",
"label": "5Y EPS CAGR",
"category": "growth",
"order": 240,
"unit": "percent",
"computation": {
"type": "cagr",
"source": "diluted_eps",
"years": 5
},
"supported_cadences": ["annual"]
},
{
"key": "market_cap",
"label": "Market Cap",
"category": "valuation",
"order": 250,
"unit": "currency",
"computation": {
"type": "simple",
"formula": "price * diluted_shares"
},
"requires_external_data": ["price"]
},
{
"key": "enterprise_value",
"label": "Enterprise Value",
"category": "valuation",
"order": 260,
"unit": "currency",
"computation": {
"type": "simple",
"formula": "market_cap + total_debt - cash_and_equivalents - short_term_investments"
},
"requires_external_data": ["market_cap"]
},
{
"key": "price_to_earnings",
"label": "Price to Earnings",
"category": "valuation",
"order": 270,
"unit": "ratio",
"computation": {
"type": "simple",
"formula": "price / diluted_eps"
},
"requires_external_data": ["price"]
},
{
"key": "price_to_fcf",
"label": "Price to FCF",
"category": "valuation",
"order": 280,
"unit": "ratio",
"computation": {
"type": "ratio",
"numerator": "market_cap",
"denominator": "free_cash_flow"
},
"requires_external_data": ["market_cap"]
},
{
"key": "price_to_book",
"label": "Price to Book",
"category": "valuation",
"order": 290,
"unit": "ratio",
"computation": {
"type": "ratio",
"numerator": "market_cap",
"denominator": "total_equity"
},
"requires_external_data": ["market_cap"]
},
{
"key": "ev_to_sales",
"label": "EV to Sales",
"category": "valuation",
"order": 300,
"unit": "ratio",
"computation": {
"type": "ratio",
"numerator": "enterprise_value",
"denominator": "revenue"
},
"requires_external_data": ["enterprise_value"]
},
{
"key": "ev_to_ebitda",
"label": "EV to EBITDA",
"category": "valuation",
"order": 310,
"unit": "ratio",
"computation": {
"type": "ratio",
"numerator": "enterprise_value",
"denominator": "ebitda"
},
"requires_external_data": ["enterprise_value"]
},
{
"key": "ev_to_fcf",
"label": "EV to FCF",
"category": "valuation",
"order": 320,
"unit": "ratio",
"computation": {
"type": "ratio",
"numerator": "enterprise_value",
"denominator": "free_cash_flow"
},
"requires_external_data": ["enterprise_value"]
}
]
}