SCINTILLA Fundamentals — Supabase Source-of-Truth

Every number on this page is read live from Supabase (scintilla-live) — FMP only ever fills that database now; this page never calls FMP directly. Universe: live from composite_staged (~211 names), not a hardcoded list.
Ticker (drives every section below, live from DB):
Loading universe from composite_staged…
A mechanical consistency check (like a balance sheet that must foot to zero) — not a screenshot, a real re-render + comparison against itself, catches wiring bugs and DB gaps automatically.

1 · Comparable Companies — NVDA vs Semis

endpoints: metrics-ratios-ttm (per symbol) + custom-dcf-advanced (growth) + search-company-screener (universe) — peer group switches with the ticker bar above
CompanyMkt CapP/EEV/EBITDAP/SP/BPEGGross MNet MD/EBetaDiv YldRev CAGR (DCF assump.)
🥇
📐
Valuation football field — what each method says the price is worth
Comps scorecard — a single measurable, peer-ranked (1 = best in group)
All of it computed live from the comps data object (ranks, medians, football-field ranges, scores) — swap the object for another ticker and the whole engine recomputes. This is the comps equivalent of your technicals Geiger score.

2 · Defining the Peer Set — Supabase ticker_cohorts

table: ticker_cohorts (curated, is_primary=true) — this replaces FMP's noisy "peers" endpoint entirely; no FMP call happens here

2.5 · Projected Path — does this trajectory look reasonable?

the assumptions you set in the DCF below drive this · sanity-check the shape before trusting any valuation
Projected path — how does the growth path you picked below (§3A) actually look?
chart:
Bars = the 5 projected years left→right; the dotted line traces the CAGR trend. Eyeball whether the trajectory is believable before trusting the valuation. Updates live with the DCF sliders and the projection-source toggle (§3A).
CAGR column = compound annual growth rate across the 5 projected years for $ metrics. All rows here are dollar figures, so all use CAGR (a margin % row would use a simple point-change instead — no % rows in this table).
Methodology — where these numbers come from. The DCF's free cash flow is built, not pulled: FMP's custom-dcf-advanced projects revenue at your growth rate, applies your EBITDA margin, then subtracts D&A, capex (3.49% of revenue) and the change in working capital (22.7% of revenue) to get unlevered FCF — so operating margin and capex are assumptions, not analyst figures. Separately, the analyst consensus in §3.5 (financial-estimates) gives revenue, EBITDA, EBIT, SG&A, net income and EPS with low/avg/high and analyst counts — but NOT capex or operating cash flow, which is why a "pure analyst FCF" still needs a capex bridge from history. Who's behind the estimates: NVDA's near-year lines carry 30–40 analysts (KeyBanc, Needham, UBS, BofA, Evercore, RBC, Morgan Stanley-tier houses); coverage thins to ~7 by FY2031. See §3.5 for the full count-by-year.

2.7 · Analyst Coverage — who's covering NVDA, and what are they saying

tables: analyst_ratings + price_target_consensus + analyst_estimates (real Supabase rows, per ticker — no FMP call from this page)
Forward estimates (analyst_estimates, annual)

3 · DCF — NVDA · sliders + modes, formulas update live

endpoint: custom-dcf-advanced · every input is a slider (drag it) with quick-set chips · formulas below show symbols then numbers
Fair value / share—
Market price$202.81
Up / downside—
Enterprise value—
Perpetuity = % of value—
Where the value comes from — explicit 5-yr cash vs the perpetuity
A · Business assumptions
Revenue growth yrs 1–5, compounding
Projection source — which growth path actually drives the DCF
EBITDA margin
Effective tax rate
bearish → bullish (sets the slider above, only used in Fixed-rate mode):
B · Discount rate — CAPM → WACC
Risk-free rate rᶠ 10Y Treasury — distinct input
Beta β vs S&P, 5-yr — default: peer median
Beta — active method
Market risk premium excess of stocks over rᶠ
Market risk premium = E(R_market) − risk-free
▸ Build your own MRP from subcomponents (optional — collapsed)
MRP = ERP = equity risk premium over the risk-free. FMP hard-codes 4.72%; this reconstructs it from parts: discount the S&P's expected cash (div + buybacks, grown 5y, terminal = rf) back to today's index level, solve for the return, subtract rf. Add a revenue-weighted country premium on top. Click "Apply" to feed it into the MRP mode above.
7457.7
1.30%
2.20%
8.50%
4.28%
0.20%
—
Cost of equity (CAPM)
WACC
NVDA ~all-equity (debt 0.2%) → WACC ≈ CoE. Leveraged names: debt weight matters.
C · Terminal value
Perpetuity growth g forever after yr 5 — distinct from rᶠ
Terminal value (Gordon growth)
g is a growth rate (perpetuity), distinct from rᶠ. The risk-free is a common reference ceiling (Damodaran), not a hard cap — a durable moat can out-earn GDP for a long time, so a higher g is defensible. Only hard rule: g < WACC.
D · Sensitivity
Impact ranking — which input moves value most (full-range swing)
Each bar = the fair-value swing when that ONE input runs across its entire range, others held at current. Longest bar = biggest lever.
① One variable — full range, with $ and up/downside
sweep:
② Two-variable matrix — pick the two axes
rows Y:
cols X:
Each cell: fair value on top, up/downside vs $202.81 below. Green above price, red below. Ranges cover the full slider span.
E · Reverse DCF — what is today's $202.81 price assuming?
🔒 Lock — every input stays at your current slider
🎯 Solve — except the ONE you pick below, which we solve for
⚖️ Target — the value that makes fair value = $202.81 (today's price)
① Which input matters most? (same tornado as §D — pick the biggest lever to solve for)
🎯 solve for (ordered by impact, biggest lever first):
② Two-variable version — what if TWO inputs move together, not one?
Same idea as above, but now both the row axis and column axis are 🔒 locked at the value shown (overriding your slider for those two only) — everything else stays at your current sliders — and we 🎯 solve for growth at each combo. Read it like a what-if grid: "if beta were X and MRP were Y, what growth would the price imply?"
Implied growth — pick the two axes (default = the two biggest levers, excluding whatever you're solving for above)
Each cell = the growth that would justify $202.81 at that row×column combo. Center cell (outlined) = your current sliders for both axes — should roughly match the ① answer above. Scan a row/column for combos where the solved number goes from plausible to absurd — that's where the market's story stops holding up.

3.5 · Analyst Consensus vs FMP Extrapolation — Visual Guide (not wired into the model)

endpoint: financial-estimates (included in your subscription — consensus, NOT TipRanks) · annual shown; quarterly also available (period=quarter)

Years across, line items down — the standard layout. Every period FMP's financial-estimates has for NVDA: 4 historical consensus years (what the Street expected then) + 6 forward years + two deliberately BLANK columns where coverage dies. Analyst counts sit at the top. Each cell = avg (low–high), $B except EPS. Gold row = FMP's DCF extrapolation for contrast: by FY2031 it sits at 2.7× the Street's own number.

🔍 The cliff is the point: counts climb into the near years (40 analysts on FY28 revenue), collapse going out (7 on FY31 EPS), and hit ZERO at FY32 — the blank columns are real, not decoration. FY22–FY25 are historical consensus snapshots (what the Street expected then — beat/miss checks come from comparing them to actuals). FMP publishes counts for revenue and EPS only; middle lines ride between those two. Quarterly (period=quarter): same six lines, ~10 forward quarters, 11–12 analysts each.
📊 Line-item depth strategy (per Alan): use the furthest-down line the estimates support, fall back up the statement as coverage thins. For NVDA all five lines exist every year, but the CONFIDENCE thins — EPS analysts drop 30→7 by FY2031 while revenue keeps 16. A consensus-based FCF proxy = EBITDA − capex − cash taxes; capex has no consensus line here, so it gets bridged from historicals (that's the "gap fill from us"). Quarterly estimates exist for near periods; annual carries the long horizon. Agreed base methodology: take the consensus TOP LINE (revenue — the most analysts, the longest horizon) and CALCULATE the bottom line ourselves via margins — using deeper consensus lines (EBITDA, net income) as cross-checks where coverage is thick enough. Paid estimate feeds (Zacks/Estimize, low hundreds/mo) logged for later — not now.
🟢 Free Buy-gauge + revision momentum (no TipRanks needed): grades-summary returns the live mix — NVDA today: 2 Strong Buy / 58 Buy / 16 Hold / 3 Sell → consensus "Buy" — and historical-ratings gives the same mix back in time = whether the Street is drifting toward or away from Buy. That IS the "Wall Street sentiment" TipRanks markets.

4 · Insider Trades — NVDA (SEC Form 4, ~2-day lag)

endpoints: search-insider-trades + insider-trade-statistics — real per-ticker Form 4 pull, switches with the ticker bar above
📡 Derived signal — computed from the transaction rows below, not typed
🛒
Open-market BUYS
—
👥
Cluster buys (≥3/30d)
—
💵
Net $ flow (discretionary)
—
🔔
Signal
—
FiledInsiderRoleTypeSharesPrice
Each row carries transaction type codes (S-Sale, P-Purchase, A-Award, G-Gift, F-InKind, M-Exempt), direct/indirect ownership, resulting position, and the SEC filing URL. Every field is machine-readable — trivially filterable to "open-market purchases only," the signal that matters. Rows shown are a curated real subset (most recent per insider) of what search-insider-trades returns.

5 · Congressional Trades — NVDA (STOCK Act, ≤45-day lag)

Move 1 gap: no senate/house trading table exists in Supabase yet

6 · Commitment of Traders — S&P 500 E-Mini, symbol=ES (CFTC, weekly)

table: cot_history (real columns: symbol, date, name, net_position, prev_net_position, market_situation, market_sentiment, reversal_trend — 5,397 rows across ~9 futures symbols: ES, NQ, GC, SI, CL, NG, DX, ZN and more)

7 · Earnings — NVDA (earnings_events + earnings_call_transcripts)

tables: earnings_events (177/211 tickers) + earnings_call_transcripts (151/211 tickers) — real per-ticker pull, switches with the ticker bar above

8 · News & Sentiment — NVDA (news + news_sentiment)

tables: news (204/211 tickers, 187,803 rows) + news_sentiment (195/211 tickers) — real per-ticker pull, switches with the ticker bar above
Generated 2026-07-18 · All data via FMP connector, live pulls · File: FMP_CAPABILITY_DEMO.html · Author: Claude for Alan
▸ How this works — what's actually wired vs. still static (read me)

Move 1 (2026-07-24): source of truth swapped from direct FMP pulls to Supabase (wadinxqplrggagkvrdag), read client-side. FMP now only ever fills the DB (master's ingest lane) — this page reads it. Universe expanded from a hardcoded 10 tickers to the live ~211-name composite_staged set. During build-out, two tables assumed empty from an earlier schema check (insider_trades, company_profile) turned out to have real data — master's ingest had caught up since. Corrected below; the running audit checker (§ top of page) is what caught the resulting rendering bugs before this went live.

🔌 DB-SOURCED — read live from Supabase on every ticker switch:

WhereWhat's DB-sourced
Universe / ticker barloadUniverse() reads composite_staged (~211 tickers) + ticker_cohorts (is_primary=true rows) once on load, powering the searchable ticker box. Not the old hardcoded 10, not the near-empty tickers table.
§1 CompsfetchCohortBundle() pulls each ticker's real cohort (ticker_cohorts) and up to 7 is_primary peers, ranked by live market cap. Multiples (P/E, P/S, P/B, EV/EBITDA, D/E, margins) are computed fresh client-side from fundamentals + TTM sums of fundamentals_history/cashflow_history + balance_history — not trusted from ratios_history's pre-computed columns, since a direct check found that table's P/S diverging significantly from a freshly-computed figure (quarterly/TTM denominator mismatch suspected). Beta column reads live from company_profile.beta — see gap note below for the ~16 tickers still missing it.
Ticker switcher / DCF basebuildBase(sym) assembles BASE from fundamentals, balance_history, cashflow_history, company_profile (beta), and live_quotes for price. setTicker() awaits this, then re-renders §1/§2/§2.7/§3/§4/§5 in sequence — same DCF math engine as before (CAPM/WACC/Gordon Growth), only the inputs are now live per-ticker DB reads instead of a 10-name hardcoded object.
§2.7 Analyst coverageLive pulls of analyst_ratings, price_target_consensus, and analyst_estimates per ticker. NVDA's own annual analyst_estimates rows (FY27–FY31) were checked against the previously hardcoded consensus path and match exactly, confirming this table is the right source. A consensus DCF path needs a full 5-year run of forward estimates to avoid a broken projection — tickers with 1-4 available years fall back to Fixed-rate, flagged. Publisher/outlet attribution (which analyst desk) has no DB equivalent — flagged, not fabricated.
§3 DCF risk-free rateloadRiskFree() reads treasury_rates.y10 — one macro rate shared across all tickers, replacing the old per-ticker hardcoded rf.
§4 InsiderLive query against insider_trades per ticker — 33,256 real rows across the universe (corrected; this table was NOT actually empty). The buy/sell classifier, 30-day cluster-buy detector, and net-flow signal run on live rows for most tickers; a genuine per-ticker zero still shows an honest gap banner.
§6 COTLive query against cot_history, symbol=ES — 5,397 real rows across ~9 futures symbols (corrected; also not actually empty — the first version queried a column name that doesn't exist in this table and silently rendered a false "empty" gap until caught).
§7 EarningsLive query against earnings_events (177/211 tickers) for the last 4 reports (EPS/revenue actual vs estimate, surprise%, beat/miss, release summary) and earnings_call_transcripts (151/211 tickers) for the latest call's AI summary. Genuine per-ticker gaps for the ~34 and ~60 tickers respectively without coverage, flagged not faked.
§8 News & SentimentLive query against news (204/211 tickers, 187,803 rows — last 8 headlines with links) and news_sentiment (195/211 tickers — a single score + article count per ticker). Same per-ticker-gap treatment for the tickers not yet covered.
Freshness everywhereupdated_ts is read per row and shown as "last true Xm/h/d ago" (red "missing" if null) via freshTag() — confidence is disclosed, not assumed.

🔴 FLAGGED GAPS — real DB gaps, shown honestly, never FMP'd-from-page or fabricated:

WhereWhat's missing and why
Beta, per-ticker195 of 211 universe tickers have a real company_profile.beta row; ~16 don't yet. Those default the DCF slider to 1.0 with a visible gap note and show "—" in §1 comps — not page-wide, not estimated, not silently defaulted.
§5 CongressNo senate-trading/house-trading equivalent table exists in Supabase at all (not even empty) — unconditional gap banner, not a per-ticker query. This is the one genuinely unbuilt category from the original Move 1 spec.
The "tail" — ~50 tickersRoughly 50 of 211 universe tickers lack full history coverage (fundamentals_history/ratios_history/analyst_estimates sit at ~161/211). Comps/CAGR/consensus-path sections for these show "—" or fall back to a flagged default rather than guessing.
Publisher/outlet attribution (§2.7)No DB field carries which analyst desk (TheFly, Benzinga, etc.) issued a rating — flagged inline where it would have appeared.

The math, for reference — unchanged by Move 1. CoE = rᶠ + (β×MRP) · WACC = (wₑ·CoE)+(w_d·k_d·(1−t)) · UFCF = EBIT(1−t)+D&A−capex−ΔNWC · TV = FCF₅(1+g)/(WACC−g) · Fair value = (ΣPV(FCF)+PV(TV)−net debt)/shares. Only the data feeding these formulas moved from a hardcoded 10-name object to live per-ticker Supabase reads — the formulas themselves were not changed.

Sources. Financials fundamentals + fundamentals_history + ratios_history + balance_history + cashflow_history · estimates/ratings/targets analyst_estimates + analyst_ratings + price_target_consensus · quote/DCF price live_quotes · beta company_profile · peer grouping ticker_cohorts · universe composite_staged · risk-free treasury_rates · insider insider_trades · COT cot_history · earnings earnings_events + earnings_call_transcripts · news news + news_sentiment. Served from git → auto-deploy; durable URL survives hub deploys.

Real next steps, in order of value: (1) once master ingests a congress-equivalent table, the page can pick it up with the same query pattern used everywhere else — the last genuinely unbuilt category, (2) feed §3.5 estimate-confidence into the reverse-DCF verdict strength, (3) backfill beta for the remaining ~16 tickers and full history for the ~50-ticker tail.