tRPC Direct Index API
tRPC Endpoints
tRPC Direct Index API
Universe catalog and constituent serving for the direct index builder.
POST
tRPC Direct Index API
The
directIndex.* namespace serves the webapp-v2 direct index builder: the
catalog of investable universes (real indices and equity sectors) and the
resolved constituent lists the builder edits against.
- Base endpoint:
POST /v1/trpc - Namespace:
directIndex.* - Auth: public (rate-limited, Tier 2)
- Primary model: CANONICAL equities. Every constituent is a canonical
underlying (e.g.
TSLA) identified byassetCanonicalIdand displayed by ticker — never a tokenized instrument (TSLAon). Instrument resolution (issuer + chain) is performed server-side by a central selection policy and surfaced asprimaryInstrumentper constituent.
Procedures
-
directIndex.getCatalog- Purpose: the grouped universe picker (Popular / Sectors / Broad Market / All) shown when starting a direct index
- Input: none
- Response: array of groups, each with:
key:popular,sectors,industries,thematic,broad_market, oralllabel: display labelentries[]: universe references —kind:index(registry-backed, e.g. SPY holdings) orsector(display-sector taxonomy)id:core.asset_indices.asset_index_iduuid for indices, or the sector category value (e.g.financials) for sectorssymbol: index symbol whenkind = indexname: display namememberCount: members in the latest snapshot;nullwhen not cheaply countable (sector universes)methodologyUrl: provider methodology link when known
- Notes: indices without weighted members in their latest snapshot (e.g. smoke/test rows) are filtered out; empty groups are omitted.
-
directIndex.getConstituents- Purpose: the resolved member list for a chosen universe — the raw input the builder applies top-N, weighting, and exclusions to
- Input:
- required
universe.kind:indexorsector - required
universe.id: index uuid or sector category value
- required
- Response:
universe: resolved universe reference (server-authoritative name)snapshotAt: ISO timestamp the constituent snapshot was resolvedresolvedChainId: the single EVM chain the instrument resolution targeted (strategies are single-chain); constituents without an instrument on this chain are markedinvestable: falseconstituents[], ranked (index weight desc for indices, market cap desc for sectors):assetCanonicalId,ticker,namesector: current display-sector classification, ornullindexWeightBps: latest index weight in basis points (nullfor sector universes)marketCapUsd: decimal string (nullwhen unknown)rank: 1-based position in the universe rankinginvestable: whether a glider-supported tokenized instrument exists onresolvedChainIdprimaryInstrument:{ assetId, chainId, issuerSlug, tokenSymbol }ornull;assetIdis the internaladdress:chainIdform used by strategy asset blocks
- Errors:
DIRECT_INDEX_NOT_FOUND(404): unknown index id or sector valueDIRECT_INDEX_EMPTY_UNIVERSE(404): universe has no current membersDIRECT_INDEX_UNAVAILABLE(500): serving dependencies unavailable
-
directIndex.getMetrics- Purpose: bulk market-data overlay for the positions table (price, 1D change, 1Y change) — the client joins it to constituents by ticker
- Input: required
tickers(1-300 canonical tickers) - Response:
{ metrics: [{ ticker, priceUsd, change1DPct, change1YPct }], yearAgoDate }—yearAgoDateis the trading day used as the 1Y baseline - Implementation: exactly two upstream shapes regardless of ticker count — chunked multi-ticker snapshots plus ONE grouped-daily aggregate for the ~1-year-ago trading day (cached per calendar day, holiday walk-back). Unknown tickers degrade to nulls; the batch never fails per-ticker.
-
directIndex.getFundamentals- Purpose: fundamentals overlay (P/E, dividend yield) — per-ticker upstream cost, so clients page requests in chunks while the table fills progressively
- Input: required
tickers(1-25) - Response:
{ summaries: [{ ticker, priceToEarnings, dividendYield, earningsPerShare, marketCap }] } - Each underlying fundamentals lookup is cached (~3 h TTL); missing fundamentals return null fields rather than failing the batch.
Semantics worth knowing
- Index membership is snapshot-layered. Ingestion appends a new batch of membership rows per sync; “current” always means the latest snapshot. The S&P 500 universe contains only holdings resolvable to Glider canonicals (~225 names, ~84% of index weight), which is ample for top-N ≤ 20 building.
- Instrument selection policy (v1): glider-supported issuer products
only; single EVM chain chosen to maximize universe coverage (priority
order
1, then56); issuer ties broken by configured priority. The policy is centralized server-side so future multi-issuer support does not change this API’s shape.