zframes 0.5.3 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +608 -9
- package/package.json +4 -4
- package/runtime/assets/{bitcoin-dominance-CxfMBVwW.js → bitcoin-dominance-CweHlZx7.js} +1 -1
- package/runtime/assets/{breakeven-BrpmE2y2.js → breakeven-CG9rKwgE.js} +1 -1
- package/runtime/assets/{breathing-Bjv7D86F.js → breathing-cDundHq6.js} +1 -1
- package/runtime/assets/{btc-blocks-Cy-YFeqC.js → btc-blocks-Do_nySHd.js} +1 -1
- package/runtime/assets/{btc-difficulty-CQ_30M6B.js → btc-difficulty-vNbz5uRo.js} +1 -1
- package/runtime/assets/{btc-fees-DsYgskwn.js → btc-fees-BmADLsmK.js} +1 -1
- package/runtime/assets/{btc-hashrate-C0dYT_WJ.js → btc-hashrate-Wx2RAG-5.js} +1 -1
- package/runtime/assets/{btc-mempool-DipekM7O.js → btc-mempool-CTwbkMUR.js} +1 -1
- package/runtime/assets/{calculator-zC8onHXp.js → calculator-mvv6XpQC.js} +1 -1
- package/runtime/assets/{checklist-baxMKxEm.js → checklist-CuEw3GpE.js} +1 -1
- package/runtime/assets/{clock-x9v1tYQm.js → clock-Cjnwi03W.js} +1 -1
- package/runtime/assets/{coin-movers-fIxzBuhy.js → coin-movers-Bcx1XR0F.js} +1 -1
- package/runtime/assets/{countdown-BlyeM771.js → countdown-Cdi5gSSu.js} +1 -1
- package/runtime/assets/cycle-shared-BOGcJDzT.js +1 -0
- package/runtime/assets/cycle-signals-CS629ZDc.js +1 -0
- package/runtime/assets/{daily-analysis-DxjxE53t.js → daily-analysis-DX8bVq85.js} +1 -1
- package/runtime/assets/{day-meter-9YEIbKbk.js → day-meter-DDfTuhms.js} +1 -1
- package/runtime/assets/defi-revenue-CpeAGwhb.js +1 -0
- package/runtime/assets/{dex-volume-chart-CIN2oKpJ.js → dex-volume-chart-sHIuJACJ.js} +1 -1
- package/runtime/assets/{dex-volume-treemap-CqHdMsnd.js → dex-volume-treemap-rSTrzz7O.js} +1 -1
- package/runtime/assets/{dice-DnddcY-J.js → dice-BrFORdjN.js} +1 -1
- package/runtime/assets/{dino-game-D6AH1SSj.js → dino-game-BOV8mV1d.js} +1 -1
- package/runtime/assets/{divider-Bu8aGlm1.js → divider-C33tH1RU.js} +1 -1
- package/runtime/assets/{drawdy-BhOQeakE.js → drawdy-BIb36JN9.js} +1 -1
- package/runtime/assets/dxy-CRifEdp_.js +1 -0
- package/runtime/assets/editor-CZoWRTJC.css +1 -0
- package/runtime/assets/editor-Dnp1eXvY.js +68 -0
- package/runtime/assets/etf-flows-BV10E2R-.js +1 -0
- package/runtime/assets/etf-flows-chart-DHu8mkXm.js +1 -0
- package/runtime/assets/eth-staking-BqWeJq6F.js +1 -0
- package/runtime/assets/eth-supply-CF-MgHjn.js +1 -0
- package/runtime/assets/{fear-greed-i87oWLnT.js → fear-greed-DuDR56h2.js} +1 -1
- package/runtime/assets/{filings-feed-Cxg9eG9S.js → filings-feed-BpfO2yF6.js} +1 -1
- package/runtime/assets/{financial-stress-Bv_reW65.js → financial-stress-BfYJdlry.js} +1 -1
- package/runtime/assets/{flappy-bird-BENHBDEL.js → flappy-bird-Dbb2UQBv.js} +1 -1
- package/runtime/assets/{fundamentals-AlhngJ8G.js → fundamentals-CUnqjF--.js} +1 -1
- package/runtime/assets/funding-comparison-CMKxW1n-.js +1 -0
- package/runtime/assets/{funding-heatmap-B4RGXX4K.js → funding-heatmap-CZWnYF8Y.js} +1 -1
- package/runtime/assets/{funding-rate-chart-Cg6gi0YC.js → funding-rate-chart-C-tpwid_.js} +1 -1
- package/runtime/assets/{fx-board-BqGsP0Xx.js → fx-board-YAy44m5d.js} +1 -1
- package/runtime/assets/{heading-Dr7Q6vy_.js → heading-uIVBEE7K.js} +1 -1
- package/runtime/assets/{holiday-calendar-C1fruUVL.js → holiday-calendar-DCj83hi2.js} +1 -1
- package/runtime/assets/{image-BulRsYTV.js → image-CITPAmp0.js} +1 -1
- package/runtime/assets/index-Bx7RmzY8.js +1 -0
- package/runtime/assets/index-CrmTiZaB.css +1 -0
- package/runtime/assets/index-DyvZokhk.js +1097 -0
- package/runtime/assets/indicators-CogwjDn9.js +1 -0
- package/runtime/assets/{inflation-pulse-Q-3bZn55.js → inflation-pulse-Bqa3-cuC.js} +1 -1
- package/runtime/assets/{journal-log-FuAPC6JH.js → journal-log-Bgjia8cQ.js} +1 -1
- package/runtime/assets/{journal-open-BREaG6Cs.js → journal-open-Bm5gwWXz.js} +1 -1
- package/runtime/assets/{journal-results-Y_pKQcgg.js → journal-results-cEWe2pbe.js} +1 -1
- package/runtime/assets/{journal-score-ZATtCKrj.js → journal-score-vmfF-9bK.js} +1 -1
- package/runtime/assets/{journal-ui-C_1ADbUX.js → journal-ui-ApBNIq5_.js} +1 -1
- package/runtime/assets/{labor-market-DVybIeSN.js → labor-market-azDXD-dR.js} +1 -1
- package/runtime/assets/{lightning-stats-ByvWkKyP.js → lightning-stats-nkyh2dOX.js} +1 -1
- package/runtime/assets/{link-grid-CJC48i5r.js → link-grid-BEo4b54T.js} +1 -1
- package/runtime/assets/ma-multiplier-BllDQMF5.js +1 -0
- package/runtime/assets/macro-calendar-Ck0dJk4p.js +1 -0
- package/runtime/assets/{market-cap-treemap-CpnOP_gY.js → market-cap-treemap-AxE2EYPO.js} +1 -1
- package/runtime/assets/{market-hours-B9zPCvQk.js → market-hours-BSwXtU8c.js} +1 -1
- package/runtime/assets/{marquee-D8GTgVmy.js → marquee-1Zr5qDJP.js} +1 -1
- package/runtime/assets/mayer-multiple-DpBJNd4d.js +1 -0
- package/runtime/assets/{mining-pools-DiyEBr6a.js → mining-pools-B-jxdTot.js} +1 -1
- package/runtime/assets/{mover-row-CO2STKkw.js → mover-row-Dg96EIqq.js} +1 -1
- package/runtime/assets/mvrv-Dx_S0TwE.js +1 -0
- package/runtime/assets/{national-debt-CcTydivP.js → national-debt-BKVBHaqm.js} +1 -1
- package/runtime/assets/{news-feed-D4xS-sLD.js → news-feed-C9itZmyp.js} +1 -1
- package/runtime/assets/{note-BXsj5NlE.js → note-BtCnmuMo.js} +1 -1
- package/runtime/assets/nupl-aIjkc57m.js +1 -0
- package/runtime/assets/{open-interest-DaFRJd2O.js → open-interest-C0ulogv6.js} +1 -1
- package/runtime/assets/{options-iv-MpSqgS3E.js → options-iv-CdUder3x.js} +1 -1
- package/runtime/assets/{options-oi-strike-BHF28ASR.js → options-oi-strike-CvCZnMCR.js} +1 -1
- package/runtime/assets/{options-put-call-_ZFaepBW.js → options-put-call-FuaDHJ-S.js} +1 -1
- package/runtime/assets/pi-cycle-BuCnLnIJ.js +1 -0
- package/runtime/assets/{pomodoro-CxHVmgqp.js → pomodoro-DDBVVcSR.js} +1 -1
- package/runtime/assets/{portfolio-allocation-Cf251dcH.js → portfolio-allocation-DAnQk_h_.js} +1 -1
- package/runtime/assets/{portfolio-common-DnESc3oR.js → portfolio-common-Bi16i0aA.js} +1 -1
- package/runtime/assets/{portfolio-holdings-2vYKEk7f.js → portfolio-holdings-MyAinCzt.js} +1 -1
- package/runtime/assets/{portfolio-value-B-7uIpG4.js → portfolio-value-BPURwKf8.js} +1 -1
- package/runtime/assets/prediction-markets-Bzy51qnV.js +1 -0
- package/runtime/assets/{price-chart-Cx_2scgb.js → price-chart-BOCD8ka3.js} +1 -1
- package/runtime/assets/{price-compare-DQcEOpnr.js → price-compare-DZlF-qhZ.js} +1 -1
- package/runtime/assets/{price-liveline-TTo-aOFd.js → price-liveline-Bl7qCd5-.js} +1 -1
- package/runtime/assets/{price-ticker-Cp7yYsNm.js → price-ticker-D2W4T02y.js} +1 -1
- package/runtime/assets/{protocol-fees-treemap-D-koQrKr.js → protocol-fees-treemap-DiIt4bfo.js} +1 -1
- package/runtime/assets/{protocol-tvl-chart-CDZkrQuF.js → protocol-tvl-chart-CmzANiR7.js} +1 -1
- package/runtime/assets/{protocol-tvl-treemap-I8fjLZU7.js → protocol-tvl-treemap-BjNPrrtL.js} +1 -1
- package/runtime/assets/puell-multiple-BGrJX43r.js +1 -0
- package/runtime/assets/{quote-CKEEp9tF.js → quote-CRM3bfI7.js} +1 -1
- package/runtime/assets/{rates-board-BElUHlYN.js → rates-board-Cb9rV0_-.js} +1 -1
- package/runtime/assets/realized-price-CYlrFa0m.js +1 -0
- package/runtime/assets/reserve-risk-Be98XUsD.js +1 -0
- package/runtime/assets/{returns-projector-DjIbvas1.js → returns-projector-D67a_yvC.js} +1 -1
- package/runtime/assets/{risk-reward-pVHqmm_g.js → risk-reward-C7WMz2od.js} +1 -1
- package/runtime/assets/rsi-momentum-IglnulkJ.js +1 -0
- package/runtime/assets/{rules-card-uMZQ6oP0.js → rules-card-DJs3fDVN.js} +1 -1
- package/runtime/assets/sector-performance-DVMaleLY.js +1 -0
- package/runtime/assets/sector-treemap-B681nSi6.js +1 -0
- package/runtime/assets/{session-progress-Djhvb1G5.js → session-progress-CZO3LqUi.js} +1 -1
- package/runtime/assets/{short-volume-CiBfmCKw.js → short-volume-l8_9Yoh3.js} +1 -1
- package/runtime/assets/{snake-CYXVjy8d.js → snake-CifbTGlZ.js} +1 -1
- package/runtime/assets/sopr-Dw_oz-mC.js +1 -0
- package/runtime/assets/{spotify-embed-CGYKFOmX.js → spotify-embed-BA0m1IRb.js} +1 -1
- package/runtime/assets/stablecoin-chains-Dd2LqqqY.js +1 -0
- package/runtime/assets/stablecoin-supply-DM4ogL4V.js +1 -0
- package/runtime/assets/{stopwatch-Cl10sfaX.js → stopwatch-Co72v-7u.js} +1 -1
- package/runtime/assets/{top-movers-vvOomk6S.js → top-movers-CLmC2TNu.js} +1 -1
- package/runtime/assets/{treasury-auctions-JMoATy9T.js → treasury-auctions-Dl9fiRgf.js} +1 -1
- package/runtime/assets/{treemap-leaf-DNIoJEK-.js → treemap-leaf-Dn31k9S9.js} +1 -1
- package/runtime/assets/trending-coins-Cpx9T6cG.js +1 -0
- package/runtime/assets/{tvl-treemap-B28_19EZ.js → tvl-treemap-e610jE8k.js} +1 -1
- package/runtime/assets/{video-DjiOnvMm.js → video-CeKjM-cE.js} +1 -1
- package/runtime/assets/volume-profile-CiMFsIBu.js +1 -0
- package/runtime/assets/{yield-curve-Dj5vJwI4.js → yield-curve-DkB0u2_Q.js} +1 -1
- package/runtime/assets/yield-scanner-BP90untT.js +1 -0
- package/runtime/index.html +2 -2
- package/runtime/assets/editor-BMMobjrE.css +0 -1
- package/runtime/assets/editor-Ca-voh3h.js +0 -68
- package/runtime/assets/index-BgSQpj_B.js +0 -936
- package/runtime/assets/index-BqHx9BjX.css +0 -1
- package/runtime/assets/index-DK7jWlTL.js +0 -1
package/dist/index.js
CHANGED
|
@@ -192,13 +192,17 @@ var DashboardSpecSchema = z2.preprocess(
|
|
|
192
192
|
),
|
|
193
193
|
gap: z2.number().min(0).default(12).describe(
|
|
194
194
|
"Pixels of space between frames (the grid gutter). 0 makes the cards flush; the editor's Layout rail exposes this as a slider."
|
|
195
|
+
),
|
|
196
|
+
paddingX: z2.number().min(0).default(0).describe(
|
|
197
|
+
"Horizontal padding (px) inside the dashboard grid \u2014 the left/right gutter between the frames and the viewport edges (the x-axis inset). 0 (default) keeps the board flush to the edges; the editor's Layout rail exposes this as a slider."
|
|
195
198
|
)
|
|
196
199
|
}).default({
|
|
197
200
|
mode: "flow-vertical",
|
|
198
201
|
columns: 12,
|
|
199
202
|
rowHeight: 96,
|
|
200
203
|
rows: 6,
|
|
201
|
-
gap: 12
|
|
204
|
+
gap: 12,
|
|
205
|
+
paddingX: 0
|
|
202
206
|
}),
|
|
203
207
|
background: BackgroundSchema.default({
|
|
204
208
|
type: "none",
|
|
@@ -426,7 +430,12 @@ var SOURCES = {
|
|
|
426
430
|
mempool: { name: "mempool.space", url: "https://mempool.space" },
|
|
427
431
|
deribit: { name: "Deribit", url: "https://www.deribit.com" },
|
|
428
432
|
coinpaprika: { name: "Coinpaprika", url: "https://coinpaprika.com" },
|
|
429
|
-
frankfurter: { name: "Frankfurter (ECB)", url: "https://frankfurter.dev" }
|
|
433
|
+
frankfurter: { name: "Frankfurter (ECB)", url: "https://frankfurter.dev" },
|
|
434
|
+
coinMetrics: { name: "Coin Metrics", url: "https://coinmetrics.io" },
|
|
435
|
+
bitcoinData: { name: "bitcoin-data.com", url: "https://bitcoin-data.com" },
|
|
436
|
+
ultrasound: { name: "ultrasound.money", url: "https://ultrasound.money" },
|
|
437
|
+
polymarket: { name: "Polymarket", url: "https://polymarket.com" },
|
|
438
|
+
sosovalue: { name: "SoSoValue", url: "https://sosovalue.com" }
|
|
430
439
|
};
|
|
431
440
|
var clockMeta = defineFrameMeta({
|
|
432
441
|
name: "clock",
|
|
@@ -772,7 +781,7 @@ var fundamentalsMeta = defineFrameMeta({
|
|
|
772
781
|
label: "Fundamentals",
|
|
773
782
|
category: "equities",
|
|
774
783
|
iconUrl: widgetIcon("fundamentals"),
|
|
775
|
-
layout: { w: 4, h:
|
|
784
|
+
layout: { w: 4, h: 4, minW: 3, minH: 3 },
|
|
776
785
|
description: "Headline financials for one US-listed company from SEC EDGAR XBRL company facts \u2014 revenue, net income, total assets, shareholders' equity, diluted EPS, and shares outstanding, each labelled with its fiscal period. Income-statement figures are the latest full fiscal year; balance-sheet figures are the latest reported quarter. Keyless official data that updates only when the company files (annual/quarterly), not a live feed. Requires the zframes runtime's data proxy (it ships with `zframes serve` / `vite dev`); resolve by ticker (bundled top-500 map) or raw SEC CIK.",
|
|
777
786
|
capabilities: ["fundamentals"],
|
|
778
787
|
source: SOURCES.secEdgar,
|
|
@@ -916,7 +925,7 @@ var journalScoreMeta = defineFrameMeta({
|
|
|
916
925
|
label: "Journal \xB7 Scoreboard",
|
|
917
926
|
category: "journal",
|
|
918
927
|
iconUrl: widgetIcon("journal-score"),
|
|
919
|
-
layout: { w: 4, h:
|
|
928
|
+
layout: { w: 4, h: 3, minW: 3, minH: 3 },
|
|
920
929
|
description: "The decision-journal scoreboard \u2014 a story, not a spreadsheet: where your judgment has an edge, where it leaks, and how calibrated your confidence is, plus a one-line read from zAI. Aggregates the calls logged via Journal \xB7 Log.",
|
|
921
930
|
capabilities: [],
|
|
922
931
|
schema: z3.object({})
|
|
@@ -1503,7 +1512,7 @@ var btcFeesMeta = defineFrameMeta({
|
|
|
1503
1512
|
label: "BTC Fees",
|
|
1504
1513
|
category: "bitcoin",
|
|
1505
1514
|
iconUrl: widgetIcon("btc-fees"),
|
|
1506
|
-
layout: { w: 3, h:
|
|
1515
|
+
layout: { w: 3, h: 3, minW: 2, minH: 3 },
|
|
1507
1516
|
description: "Recommended Bitcoin on-chain fee rates (sat/vB) from mempool.space \u2014 the next-block ('fastest'), ~30-minute, ~1-hour, economy, and minimum tiers, as a compact gauge. Live mempool data, keyless; updates every ~30s.",
|
|
1508
1517
|
capabilities: ["btc-fees"],
|
|
1509
1518
|
source: SOURCES.mempool,
|
|
@@ -1667,6 +1676,377 @@ var coinMoversMeta = defineFrameMeta({
|
|
|
1667
1676
|
)
|
|
1668
1677
|
})
|
|
1669
1678
|
});
|
|
1679
|
+
var mvrvMeta = defineFrameMeta({
|
|
1680
|
+
name: "mvrv",
|
|
1681
|
+
label: "MVRV Ratio",
|
|
1682
|
+
category: "onchain",
|
|
1683
|
+
iconUrl: widgetIcon("mvrv"),
|
|
1684
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1685
|
+
description: "Bitcoin MVRV ratio \u2014 market cap \xF7 realized cap. Above ~3 historically marks cycle tops (overvalued); below ~1 marks deep value near bottoms. Shows the current ratio, its valuation zone, the MVRV Z-score, and a history sparkline. Keyless on-chain data from Coin Metrics.",
|
|
1686
|
+
capabilities: ["onchain-valuation"],
|
|
1687
|
+
source: SOURCES.coinMetrics,
|
|
1688
|
+
schema: z3.object({
|
|
1689
|
+
window: z3.enum(["1Y", "2Y", "4Y", "all"]).default("all").describe("How much history the sparkline shows.")
|
|
1690
|
+
})
|
|
1691
|
+
});
|
|
1692
|
+
var nuplMeta = defineFrameMeta({
|
|
1693
|
+
name: "nupl",
|
|
1694
|
+
label: "NUPL",
|
|
1695
|
+
category: "onchain",
|
|
1696
|
+
iconUrl: widgetIcon("nupl"),
|
|
1697
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1698
|
+
description: "Net Unrealized Profit/Loss \u2014 the share of Bitcoin's market cap held in unrealized profit. Maps to cycle sentiment phases: Capitulation (<0), Hope/Fear (0\u201325%), Optimism (25\u201350%), Belief (50\u201375%), Euphoria/Greed (>75%). Derived from MVRV; keyless Coin Metrics data.",
|
|
1699
|
+
capabilities: ["onchain-valuation"],
|
|
1700
|
+
source: SOURCES.coinMetrics,
|
|
1701
|
+
schema: z3.object({
|
|
1702
|
+
window: z3.enum(["1Y", "2Y", "4Y", "all"]).default("all").describe("How much history the sparkline shows.")
|
|
1703
|
+
})
|
|
1704
|
+
});
|
|
1705
|
+
var soprMeta = defineFrameMeta({
|
|
1706
|
+
name: "sopr",
|
|
1707
|
+
label: "SOPR",
|
|
1708
|
+
category: "onchain",
|
|
1709
|
+
iconUrl: widgetIcon("sopr"),
|
|
1710
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1711
|
+
description: "Spent Output Profit Ratio \u2014 whether coins moving on-chain are, on average, being sold in profit (>1) or loss (<1). Sustained dips below 1 mark capitulation; resets to ~1 in bull markets are healthy. Keyless full-history data from bitcoin-data.com (polled once daily).",
|
|
1712
|
+
capabilities: ["onchain-cycle-extras"],
|
|
1713
|
+
source: SOURCES.bitcoinData,
|
|
1714
|
+
schema: z3.object({
|
|
1715
|
+
window: z3.enum(["90D", "180D", "1Y"]).default("1Y").describe("How much history the sparkline shows.")
|
|
1716
|
+
})
|
|
1717
|
+
});
|
|
1718
|
+
var puellMultipleMeta = defineFrameMeta({
|
|
1719
|
+
name: "puell-multiple",
|
|
1720
|
+
label: "Puell Multiple",
|
|
1721
|
+
category: "onchain",
|
|
1722
|
+
iconUrl: widgetIcon("puell-multiple"),
|
|
1723
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1724
|
+
description: "Puell Multiple \u2014 daily miner issuance in USD \xF7 its 365-day average. High values (>4) mark cycle tops where miner revenue is stretched; low values (\u22640.5) mark miner capitulation near bottoms. Keyless data from bitcoin-data.com (polled once daily).",
|
|
1725
|
+
capabilities: ["onchain-cycle-extras"],
|
|
1726
|
+
source: SOURCES.bitcoinData,
|
|
1727
|
+
schema: z3.object({
|
|
1728
|
+
window: z3.enum(["90D", "180D", "1Y"]).default("1Y").describe("How much history the sparkline shows.")
|
|
1729
|
+
})
|
|
1730
|
+
});
|
|
1731
|
+
var mayerMultipleMeta = defineFrameMeta({
|
|
1732
|
+
name: "mayer-multiple",
|
|
1733
|
+
label: "Mayer Multiple",
|
|
1734
|
+
category: "onchain",
|
|
1735
|
+
iconUrl: widgetIcon("mayer-multiple"),
|
|
1736
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1737
|
+
description: "Mayer Multiple \u2014 BTC price \xF7 its 200-day moving average. Above ~2.4 has historically been overheated; below ~0.8 marks value zones. Computed in-browser from a keyless long daily price series (Coin Metrics).",
|
|
1738
|
+
capabilities: ["price-history-daily"],
|
|
1739
|
+
source: SOURCES.coinMetrics,
|
|
1740
|
+
schema: z3.object({
|
|
1741
|
+
window: z3.enum(["1Y", "2Y", "4Y", "all"]).default("2Y").describe("How much history the sparkline shows.")
|
|
1742
|
+
})
|
|
1743
|
+
});
|
|
1744
|
+
var piCycleMeta = defineFrameMeta({
|
|
1745
|
+
name: "pi-cycle",
|
|
1746
|
+
label: "Pi Cycle Top",
|
|
1747
|
+
category: "onchain",
|
|
1748
|
+
iconUrl: widgetIcon("pi-cycle"),
|
|
1749
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1750
|
+
description: "Pi Cycle Top indicator \u2014 the ratio of the 111-day MA to 2\xD7 the 350-day MA. When it crosses 1 (the 111DMA overtakes 2\xD7350DMA) it has historically pinpointed cycle tops within days. Computed in-browser from a keyless long daily price series (Coin Metrics).",
|
|
1751
|
+
capabilities: ["price-history-daily"],
|
|
1752
|
+
source: SOURCES.coinMetrics,
|
|
1753
|
+
schema: z3.object({
|
|
1754
|
+
window: z3.enum(["1Y", "2Y", "4Y", "all"]).default("2Y").describe("How much history the sparkline shows.")
|
|
1755
|
+
})
|
|
1756
|
+
});
|
|
1757
|
+
var maMultiplierMeta = defineFrameMeta({
|
|
1758
|
+
name: "ma-multiplier",
|
|
1759
|
+
label: "MA Multiplier",
|
|
1760
|
+
category: "onchain",
|
|
1761
|
+
iconUrl: widgetIcon("ma-multiplier"),
|
|
1762
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1763
|
+
description: "Long moving-average multiplier \u2014 BTC price \xF7 its multi-year moving average (2-year or 4-year). The 2Y band flags a buy zone below \xF71.5 and sell tiers at \xD72\u2013\xD75; the 4Y multiple marks tops above ~3.5\xD7. Computed in-browser from a keyless long daily price series (Coin Metrics).",
|
|
1764
|
+
capabilities: ["price-history-daily"],
|
|
1765
|
+
source: SOURCES.coinMetrics,
|
|
1766
|
+
schema: z3.object({
|
|
1767
|
+
years: z3.enum(["2", "4"]).default("2").describe("Moving-average window in years."),
|
|
1768
|
+
window: z3.enum(["2Y", "4Y", "all"]).default("all").describe("How much history the sparkline shows.")
|
|
1769
|
+
})
|
|
1770
|
+
});
|
|
1771
|
+
var rsiMomentumMeta = defineFrameMeta({
|
|
1772
|
+
name: "rsi-momentum",
|
|
1773
|
+
label: "RSI Momentum",
|
|
1774
|
+
category: "markets",
|
|
1775
|
+
iconUrl: widgetIcon("rsi-momentum"),
|
|
1776
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1777
|
+
description: "Wilder RSI on BTC daily closes with a 55/45 momentum regime: above 55 = risk-on, below 45 = risk-off, in between = neutral. Also flags classic overbought (\u226580) / oversold (\u226430) extremes. Computed in-browser from a keyless long daily price series (Coin Metrics).",
|
|
1778
|
+
capabilities: ["price-history-daily"],
|
|
1779
|
+
source: SOURCES.coinMetrics,
|
|
1780
|
+
schema: z3.object({
|
|
1781
|
+
period: z3.number().int().min(2).max(50).default(14).describe("RSI lookback period in days."),
|
|
1782
|
+
window: z3.enum(["90D", "180D", "1Y", "2Y"]).default("180D").describe("How much history the sparkline shows.")
|
|
1783
|
+
})
|
|
1784
|
+
});
|
|
1785
|
+
var volumeProfileMeta = defineFrameMeta({
|
|
1786
|
+
name: "volume-profile",
|
|
1787
|
+
label: "Volume Profile",
|
|
1788
|
+
category: "markets",
|
|
1789
|
+
iconUrl: widgetIcon("volume-profile"),
|
|
1790
|
+
layout: { w: 4, h: 4, minW: 3, minH: 3 },
|
|
1791
|
+
description: "Volume-by-price histogram over a lookback window \u2014 the Point of Control (POC, highest-volume price) and the 70% Value Area (VAH/VAL) that frame support/resistance. Computed in-browser from OHLCV candles. Pass any tradable symbol (crypto or a HIP-3 equity like 'xyz:TSLA').",
|
|
1792
|
+
capabilities: ["ohlcv"],
|
|
1793
|
+
source: SOURCES.hyperliquid,
|
|
1794
|
+
schema: z3.object({
|
|
1795
|
+
symbol: z3.string().default("BTC").describe(
|
|
1796
|
+
"Symbol to profile, e.g. 'BTC', 'ETH', or a HIP-3 equity 'xyz:TSLA'."
|
|
1797
|
+
),
|
|
1798
|
+
interval: z3.enum(["1h", "4h", "1d"]).default("1d").describe("Candle interval."),
|
|
1799
|
+
lookbackDays: z3.number().int().min(7).max(365).default(90).describe("How many days of candles to build the profile from."),
|
|
1800
|
+
bins: z3.number().int().min(8).max(48).default(24).describe("Number of price buckets in the histogram.")
|
|
1801
|
+
})
|
|
1802
|
+
});
|
|
1803
|
+
var dxyMeta = defineFrameMeta({
|
|
1804
|
+
name: "dxy",
|
|
1805
|
+
label: "Dollar Index (DXY)",
|
|
1806
|
+
category: "macro",
|
|
1807
|
+
iconUrl: widgetIcon("dxy"),
|
|
1808
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1809
|
+
description: "US Dollar Index (DXY) \u2014 the dollar's strength vs a basket of six major currencies. A rising DXY is a macro headwind for risk assets (incl. BTC); a falling DXY a tailwind. Computed as the ICE-weighted geometric mean of keyless ECB reference rates (daily granularity).",
|
|
1810
|
+
capabilities: ["dollar-index"],
|
|
1811
|
+
source: SOURCES.frankfurter,
|
|
1812
|
+
schema: z3.object({})
|
|
1813
|
+
});
|
|
1814
|
+
var cycleSignalsMeta = defineFrameMeta({
|
|
1815
|
+
name: "cycle-signals",
|
|
1816
|
+
label: "Cycle Signals",
|
|
1817
|
+
category: "onchain",
|
|
1818
|
+
iconUrl: widgetIcon("cycle-signals"),
|
|
1819
|
+
layout: { w: 4, h: 5, minW: 3, minH: 3 },
|
|
1820
|
+
description: "A cycle top- or bottom-signal checklist \u2014 MVRV, MVRV Z-score, NUPL, Mayer Multiple, Puell, RSI, and Pi Cycle each checked against its historical extreme, with a live 'X of N firing' tally. A capstone that aggregates the on-chain and cycle metrics into one 'how late in the cycle are we' read. Keyless (Coin Metrics + bitcoin-data.com).",
|
|
1821
|
+
capabilities: [
|
|
1822
|
+
"onchain-valuation",
|
|
1823
|
+
"onchain-cycle-extras",
|
|
1824
|
+
"price-history-daily"
|
|
1825
|
+
],
|
|
1826
|
+
source: [SOURCES.coinMetrics, SOURCES.bitcoinData],
|
|
1827
|
+
schema: z3.object({
|
|
1828
|
+
mode: z3.enum(["peak", "bottom"]).default("peak").describe(
|
|
1829
|
+
"Which checklist to show: cycle-top ('peak') or cycle-bottom ('bottom') signals."
|
|
1830
|
+
)
|
|
1831
|
+
})
|
|
1832
|
+
});
|
|
1833
|
+
var stablecoinSupplyMeta = defineFrameMeta({
|
|
1834
|
+
name: "stablecoin-supply",
|
|
1835
|
+
label: "Stablecoin Supply",
|
|
1836
|
+
category: "crypto",
|
|
1837
|
+
iconUrl: widgetIcon("stablecoin-supply"),
|
|
1838
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1839
|
+
description: "Total USD-stablecoin circulating supply \u2014 a market-wide liquidity gauge. Rising supply = fresh capital entering crypto (risk-on dry powder); contraction = risk-off. Shows the total, 1d/7d/30d change, and the largest chains. Keyless (DeFiLlama).",
|
|
1840
|
+
capabilities: ["stablecoins"],
|
|
1841
|
+
source: SOURCES.defillama,
|
|
1842
|
+
schema: z3.object({})
|
|
1843
|
+
});
|
|
1844
|
+
var yieldScannerMeta = defineFrameMeta({
|
|
1845
|
+
name: "yield-scanner",
|
|
1846
|
+
label: "Yield Scanner",
|
|
1847
|
+
category: "crypto",
|
|
1848
|
+
iconUrl: widgetIcon("yield-scanner"),
|
|
1849
|
+
layout: { w: 5, h: 4, minW: 3, minH: 3 },
|
|
1850
|
+
description: "Top DeFi yield pools ranked by APY, across every chain and protocol \u2014 the 'where's the yield' board. Filter to stablecoin pools or a TVL floor. Shows APY (base + reward), TVL, chain, and IL risk. Keyless (DeFiLlama yields).",
|
|
1851
|
+
capabilities: ["yields"],
|
|
1852
|
+
source: SOURCES.defillama,
|
|
1853
|
+
schema: z3.object({
|
|
1854
|
+
limit: z3.number().int().min(3).max(20).default(8).describe("How many pools to list."),
|
|
1855
|
+
stablecoinOnly: z3.boolean().default(false).describe("Only show stablecoin pools (lower impermanent-loss risk)."),
|
|
1856
|
+
minTvlUsd: z3.number().min(0).default(1e6).describe("Minimum pool TVL in USD \u2014 a liquidity floor to hide dust.")
|
|
1857
|
+
})
|
|
1858
|
+
});
|
|
1859
|
+
var defiRevenueMeta = defineFrameMeta({
|
|
1860
|
+
name: "defi-revenue",
|
|
1861
|
+
label: "DeFi Fees & Revenue",
|
|
1862
|
+
category: "crypto",
|
|
1863
|
+
iconUrl: widgetIcon("defi-revenue"),
|
|
1864
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1865
|
+
description: "Aggregate DeFi protocol fees across all of crypto \u2014 trailing-24h total with a daily trend. A read on real on-chain economic activity. Keyless (DeFiLlama).",
|
|
1866
|
+
capabilities: ["fees-overview"],
|
|
1867
|
+
source: SOURCES.defillama,
|
|
1868
|
+
schema: z3.object({})
|
|
1869
|
+
});
|
|
1870
|
+
var fundingComparisonMeta = defineFrameMeta({
|
|
1871
|
+
name: "funding-comparison",
|
|
1872
|
+
label: "Cross-Venue Funding",
|
|
1873
|
+
category: "derivatives",
|
|
1874
|
+
iconUrl: widgetIcon("funding-comparison"),
|
|
1875
|
+
layout: { w: 5, h: 4, minW: 3, minH: 3 },
|
|
1876
|
+
description: "Predicted perpetual funding rates compared across venues (Hyperliquid vs Binance vs Bybit), annualized, per coin \u2014 ranked by the cross-venue spread. A large spread flags a funding-arbitrage or crowded-positioning signal. Keyless (Hyperliquid predicted fundings).",
|
|
1877
|
+
capabilities: ["funding-comparison"],
|
|
1878
|
+
source: SOURCES.hyperliquid,
|
|
1879
|
+
schema: z3.object({
|
|
1880
|
+
limit: z3.number().int().min(3).max(20).default(8).describe("How many coins (by funding spread) to show.")
|
|
1881
|
+
})
|
|
1882
|
+
});
|
|
1883
|
+
var ethSupplyMeta = defineFrameMeta({
|
|
1884
|
+
name: "eth-supply",
|
|
1885
|
+
label: "ETH Ultrasound",
|
|
1886
|
+
category: "crypto",
|
|
1887
|
+
iconUrl: widgetIcon("eth-supply"),
|
|
1888
|
+
layout: { w: 4, h: 3, minW: 2, minH: 2 },
|
|
1889
|
+
description: "Ethereum supply economics \u2014 EIP-1559 burn vs PoS issuance and the resulting net annual supply growth. Negative growth = deflationary ('ultrasound money'). Shows the net rate, burn/issuance, and vs the counterfactual PoW issuance. Keyless (ultrasound.money).",
|
|
1890
|
+
capabilities: ["eth-supply"],
|
|
1891
|
+
source: SOURCES.ultrasound,
|
|
1892
|
+
schema: z3.object({})
|
|
1893
|
+
});
|
|
1894
|
+
var ethStakingMeta = defineFrameMeta({
|
|
1895
|
+
name: "eth-staking",
|
|
1896
|
+
label: "ETH Staking APR",
|
|
1897
|
+
category: "crypto",
|
|
1898
|
+
iconUrl: widgetIcon("eth-staking"),
|
|
1899
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
1900
|
+
description: "Ethereum staking yield \u2014 total validator APR broken into consensus issuance, MEV, and priority tips. The 'risk-free' ETH rate. Keyless (ultrasound.money).",
|
|
1901
|
+
capabilities: ["eth-supply"],
|
|
1902
|
+
source: SOURCES.ultrasound,
|
|
1903
|
+
schema: z3.object({})
|
|
1904
|
+
});
|
|
1905
|
+
var predictionMarketsMeta = defineFrameMeta({
|
|
1906
|
+
name: "prediction-markets",
|
|
1907
|
+
label: "Prediction Markets",
|
|
1908
|
+
category: "sentiment",
|
|
1909
|
+
iconUrl: widgetIcon("prediction-markets"),
|
|
1910
|
+
layout: { w: 4, h: 4, minW: 3, minH: 3 },
|
|
1911
|
+
description: "Live Polymarket odds \u2014 the highest-volume open prediction markets with their market-implied probabilities (macro, rates, crypto, politics). A real-money sentiment gauge. Keyless (Polymarket Gamma API).",
|
|
1912
|
+
capabilities: ["prediction-markets"],
|
|
1913
|
+
source: SOURCES.polymarket,
|
|
1914
|
+
schema: z3.object({
|
|
1915
|
+
limit: z3.number().int().min(3).max(20).default(6).describe("How many markets (by volume) to show.")
|
|
1916
|
+
})
|
|
1917
|
+
});
|
|
1918
|
+
var etfFlowsMeta = defineFrameMeta({
|
|
1919
|
+
name: "etf-flows",
|
|
1920
|
+
label: "Spot ETF Flows",
|
|
1921
|
+
category: "crypto",
|
|
1922
|
+
iconUrl: widgetIcon("etf-flows"),
|
|
1923
|
+
layout: { w: 4, h: 4, minW: 3, minH: 3 },
|
|
1924
|
+
description: "Spot Bitcoin or Ethereum ETF daily net flows \u2014 per-issuer (IBIT, FBTC, GBTC, \u2026) plus the total, with a recent trend. The biggest institutional-demand signal. Keyless (SoSoValue); best-effort, may show empty if the source is unavailable.",
|
|
1925
|
+
capabilities: ["etf-flows"],
|
|
1926
|
+
source: SOURCES.sosovalue,
|
|
1927
|
+
schema: z3.object({
|
|
1928
|
+
asset: z3.enum(["btc", "eth"]).default("btc").describe("Which spot-ETF complex to show."),
|
|
1929
|
+
limit: z3.number().int().min(3).max(15).default(8).describe("How many issuers to list.")
|
|
1930
|
+
})
|
|
1931
|
+
});
|
|
1932
|
+
var trendingCoinsMeta = defineFrameMeta({
|
|
1933
|
+
name: "trending-coins",
|
|
1934
|
+
label: "Trending Coins",
|
|
1935
|
+
category: "crypto",
|
|
1936
|
+
iconUrl: widgetIcon("trending-coins"),
|
|
1937
|
+
layout: { w: 3, h: 4, minW: 2, minH: 3 },
|
|
1938
|
+
description: "The coins with the most search interest right now on CoinGecko \u2014 a retail-attention gauge. Shows rank, price, and 24h change. Keyless (CoinGecko).",
|
|
1939
|
+
capabilities: ["trending-coins"],
|
|
1940
|
+
source: SOURCES.coingecko,
|
|
1941
|
+
schema: z3.object({
|
|
1942
|
+
limit: z3.number().int().min(3).max(15).default(7).describe("How many trending coins to show.")
|
|
1943
|
+
})
|
|
1944
|
+
});
|
|
1945
|
+
var sectorPerformanceMeta = defineFrameMeta({
|
|
1946
|
+
name: "sector-performance",
|
|
1947
|
+
label: "Sector Performance",
|
|
1948
|
+
category: "crypto",
|
|
1949
|
+
iconUrl: widgetIcon("sector-performance"),
|
|
1950
|
+
layout: { w: 4, h: 4, minW: 3, minH: 3 },
|
|
1951
|
+
description: "Crypto sector rotation \u2014 market categories (L1s, DeFi, AI, memes, RWA, \u2026) ranked by 24h market-cap change. Shows where capital is rotating. Keyless (CoinGecko categories).",
|
|
1952
|
+
capabilities: ["sector-performance"],
|
|
1953
|
+
source: SOURCES.coingecko,
|
|
1954
|
+
schema: z3.object({
|
|
1955
|
+
limit: z3.number().int().min(4).max(30).default(10).describe("How many sectors to show.")
|
|
1956
|
+
})
|
|
1957
|
+
});
|
|
1958
|
+
var macroCalendarMeta = defineFrameMeta({
|
|
1959
|
+
name: "macro-calendar",
|
|
1960
|
+
label: "Macro Calendar",
|
|
1961
|
+
category: "macro",
|
|
1962
|
+
iconUrl: widgetIcon("macro-calendar"),
|
|
1963
|
+
layout: { w: 4, h: 4, minW: 3, minH: 2 },
|
|
1964
|
+
description: "Countdown to upcoming scheduled macro events \u2014 defaults to the 2026 FOMC rate decisions, fully editable. No data feed; the dates are known in advance.",
|
|
1965
|
+
capabilities: [],
|
|
1966
|
+
schema: z3.object({
|
|
1967
|
+
limit: z3.number().int().min(1).max(12).default(5).describe("How many upcoming events to show."),
|
|
1968
|
+
events: z3.array(
|
|
1969
|
+
z3.object({
|
|
1970
|
+
date: z3.string().describe("Event date, ISO YYYY-MM-DD."),
|
|
1971
|
+
label: z3.string().describe("Event name, e.g. 'FOMC decision'.")
|
|
1972
|
+
})
|
|
1973
|
+
).default([
|
|
1974
|
+
{ date: "2026-07-29", label: "FOMC decision" },
|
|
1975
|
+
{ date: "2026-09-16", label: "FOMC decision" },
|
|
1976
|
+
{ date: "2026-10-28", label: "FOMC decision" },
|
|
1977
|
+
{ date: "2026-12-09", label: "FOMC decision" },
|
|
1978
|
+
{ date: "2027-01-27", label: "FOMC decision" }
|
|
1979
|
+
]).describe(
|
|
1980
|
+
"Scheduled events (date + label). Defaults to the 2026 FOMC meetings; edit to add CPI/NFP/earnings dates."
|
|
1981
|
+
)
|
|
1982
|
+
})
|
|
1983
|
+
});
|
|
1984
|
+
var stablecoinChainsMeta = defineFrameMeta({
|
|
1985
|
+
name: "stablecoin-chains",
|
|
1986
|
+
label: "Stablecoin Chains",
|
|
1987
|
+
category: "crypto",
|
|
1988
|
+
iconUrl: widgetIcon("stablecoin-chains"),
|
|
1989
|
+
layout: { w: 5, h: 4, minW: 4, minH: 3 },
|
|
1990
|
+
description: "Where stablecoin liquidity sits \u2014 a treemap of the largest chains by stablecoin circulating supply. Complements the Stablecoin Supply total with the cross-chain distribution. Keyless (DeFiLlama).",
|
|
1991
|
+
capabilities: ["stablecoins"],
|
|
1992
|
+
source: SOURCES.defillama,
|
|
1993
|
+
schema: z3.object({
|
|
1994
|
+
limit: z3.number().int().min(4).max(16).default(12).describe("How many chains to show in the treemap.")
|
|
1995
|
+
})
|
|
1996
|
+
});
|
|
1997
|
+
var sectorTreemapMeta = defineFrameMeta({
|
|
1998
|
+
name: "sector-treemap",
|
|
1999
|
+
label: "Sector Treemap",
|
|
2000
|
+
category: "crypto",
|
|
2001
|
+
iconUrl: widgetIcon("sector-treemap"),
|
|
2002
|
+
layout: { w: 6, h: 4, minW: 4, minH: 3 },
|
|
2003
|
+
description: "Crypto sector rotation as a treemap \u2014 each category sized by market cap and colored by 24h change (green up / red down). The at-a-glance view of where capital is flowing. Keyless (CoinGecko categories).",
|
|
2004
|
+
capabilities: ["sector-performance"],
|
|
2005
|
+
source: SOURCES.coingecko,
|
|
2006
|
+
schema: z3.object({
|
|
2007
|
+
limit: z3.number().int().min(6).max(30).default(16).describe("How many sectors to show.")
|
|
2008
|
+
})
|
|
2009
|
+
});
|
|
2010
|
+
var etfFlowsChartMeta = defineFrameMeta({
|
|
2011
|
+
name: "etf-flows-chart",
|
|
2012
|
+
label: "ETF Flows Chart",
|
|
2013
|
+
category: "crypto",
|
|
2014
|
+
iconUrl: widgetIcon("etf-flows-chart"),
|
|
2015
|
+
layout: { w: 6, h: 3, minW: 3, minH: 3 },
|
|
2016
|
+
description: "Spot BTC or ETH ETF daily net flows over time \u2014 the inflow/outflow trend as a line, complementing the per-issuer snapshot. Keyless (SoSoValue); best-effort, may be empty if the source is unavailable.",
|
|
2017
|
+
capabilities: ["etf-flows"],
|
|
2018
|
+
source: SOURCES.sosovalue,
|
|
2019
|
+
schema: z3.object({
|
|
2020
|
+
asset: z3.enum(["btc", "eth"]).default("btc").describe("Which spot-ETF complex to chart."),
|
|
2021
|
+
lookback: z3.enum(["1M", "3M", "6M"]).default("3M").describe("History window for the flow chart.")
|
|
2022
|
+
})
|
|
2023
|
+
});
|
|
2024
|
+
var realizedPriceMeta = defineFrameMeta({
|
|
2025
|
+
name: "realized-price",
|
|
2026
|
+
label: "Realized Price",
|
|
2027
|
+
category: "onchain",
|
|
2028
|
+
iconUrl: widgetIcon("realized-price"),
|
|
2029
|
+
layout: { w: 6, h: 3, minW: 4, minH: 3 },
|
|
2030
|
+
description: "Bitcoin market price vs realized price \u2014 the on-chain cost basis of all coins. Market above realized = aggregate profit; crossing below realized has marked cycle bottoms. Keyless (Coin Metrics).",
|
|
2031
|
+
capabilities: ["onchain-valuation"],
|
|
2032
|
+
source: SOURCES.coinMetrics,
|
|
2033
|
+
schema: z3.object({
|
|
2034
|
+
window: z3.enum(["1Y", "2Y", "4Y", "all"]).default("2Y").describe("How much history the chart shows.")
|
|
2035
|
+
})
|
|
2036
|
+
});
|
|
2037
|
+
var reserveRiskMeta = defineFrameMeta({
|
|
2038
|
+
name: "reserve-risk",
|
|
2039
|
+
label: "Reserve Risk",
|
|
2040
|
+
category: "onchain",
|
|
2041
|
+
iconUrl: widgetIcon("reserve-risk"),
|
|
2042
|
+
layout: { w: 3, h: 3, minW: 2, minH: 2 },
|
|
2043
|
+
description: "Reserve Risk \u2014 long-term-holder conviction relative to price. Low values = strong conviction at a low price (attractive risk/reward, cycle-bottom territory); high values = conviction spent into a high price. Keyless (bitcoin-data.com).",
|
|
2044
|
+
capabilities: ["onchain-cycle-extras"],
|
|
2045
|
+
source: SOURCES.bitcoinData,
|
|
2046
|
+
schema: z3.object({
|
|
2047
|
+
window: z3.enum(["90D", "180D", "1Y"]).default("1Y").describe("How much history the sparkline shows.")
|
|
2048
|
+
})
|
|
2049
|
+
});
|
|
1670
2050
|
var frameMetas = [
|
|
1671
2051
|
newsFeedMeta,
|
|
1672
2052
|
portfolioValueMeta,
|
|
@@ -1726,7 +2106,34 @@ var frameMetas = [
|
|
|
1726
2106
|
optionsPutCallMeta,
|
|
1727
2107
|
optionsIvMeta,
|
|
1728
2108
|
optionsOiStrikeMeta,
|
|
1729
|
-
coinMoversMeta
|
|
2109
|
+
coinMoversMeta,
|
|
2110
|
+
mvrvMeta,
|
|
2111
|
+
nuplMeta,
|
|
2112
|
+
soprMeta,
|
|
2113
|
+
puellMultipleMeta,
|
|
2114
|
+
mayerMultipleMeta,
|
|
2115
|
+
piCycleMeta,
|
|
2116
|
+
maMultiplierMeta,
|
|
2117
|
+
rsiMomentumMeta,
|
|
2118
|
+
volumeProfileMeta,
|
|
2119
|
+
dxyMeta,
|
|
2120
|
+
cycleSignalsMeta,
|
|
2121
|
+
stablecoinSupplyMeta,
|
|
2122
|
+
yieldScannerMeta,
|
|
2123
|
+
defiRevenueMeta,
|
|
2124
|
+
fundingComparisonMeta,
|
|
2125
|
+
ethSupplyMeta,
|
|
2126
|
+
ethStakingMeta,
|
|
2127
|
+
predictionMarketsMeta,
|
|
2128
|
+
etfFlowsMeta,
|
|
2129
|
+
trendingCoinsMeta,
|
|
2130
|
+
sectorPerformanceMeta,
|
|
2131
|
+
macroCalendarMeta,
|
|
2132
|
+
stablecoinChainsMeta,
|
|
2133
|
+
sectorTreemapMeta,
|
|
2134
|
+
etfFlowsChartMeta,
|
|
2135
|
+
realizedPriceMeta,
|
|
2136
|
+
reserveRiskMeta
|
|
1730
2137
|
];
|
|
1731
2138
|
var allFrameMetas = [
|
|
1732
2139
|
...frameMetas,
|
|
@@ -3120,6 +3527,8 @@ var AlternativeMeProvider = class {
|
|
|
3120
3527
|
// ../provider-coingecko/src/index.ts
|
|
3121
3528
|
var GLOBAL_URL = "https://api.coingecko.com/api/v3/global";
|
|
3122
3529
|
var MARKETS_URL = "https://api.coingecko.com/api/v3/coins/markets?vs_currency=usd&order=market_cap_desc&per_page=50&page=1&sparkline=false&price_change_percentage=24h";
|
|
3530
|
+
var TRENDING_URL = "https://api.coingecko.com/api/v3/search/trending";
|
|
3531
|
+
var CATEGORIES_URL = "https://api.coingecko.com/api/v3/coins/categories";
|
|
3123
3532
|
var globalCache = new TtlCache({
|
|
3124
3533
|
namespace: "zframes:coingecko:global",
|
|
3125
3534
|
ttlMs: 12 * 6e4,
|
|
@@ -3130,12 +3539,55 @@ var marketsCache = new TtlCache({
|
|
|
3130
3539
|
ttlMs: 10 * 6e4,
|
|
3131
3540
|
persist: true
|
|
3132
3541
|
});
|
|
3542
|
+
var trendingCache = new TtlCache({
|
|
3543
|
+
namespace: "zframes:coingecko:trending",
|
|
3544
|
+
ttlMs: 10 * 6e4,
|
|
3545
|
+
persist: true
|
|
3546
|
+
});
|
|
3547
|
+
var categoriesCache = new TtlCache({
|
|
3548
|
+
namespace: "zframes:coingecko:categories",
|
|
3549
|
+
ttlMs: 12 * 6e4,
|
|
3550
|
+
persist: true
|
|
3551
|
+
});
|
|
3133
3552
|
var CoinGeckoProvider = class {
|
|
3134
3553
|
name = "coingecko";
|
|
3135
3554
|
capabilities = [
|
|
3136
3555
|
"global-market",
|
|
3137
|
-
"coin-markets"
|
|
3556
|
+
"coin-markets",
|
|
3557
|
+
"trending-coins",
|
|
3558
|
+
"sector-performance"
|
|
3138
3559
|
];
|
|
3560
|
+
async getTrendingCoins() {
|
|
3561
|
+
return trendingCache.get("trending", async () => {
|
|
3562
|
+
const body = await fetchJson(TRENDING_URL);
|
|
3563
|
+
if (!Array.isArray(body?.coins))
|
|
3564
|
+
throw new Error("coingecko trending: unexpected response shape");
|
|
3565
|
+
return body.coins.map(({ item }) => {
|
|
3566
|
+
const price = Number(item.data?.price);
|
|
3567
|
+
const chg = Number(item.data?.price_change_percentage_24h?.usd);
|
|
3568
|
+
return {
|
|
3569
|
+
id: item.id,
|
|
3570
|
+
name: item.name,
|
|
3571
|
+
symbol: (item.symbol ?? "").toUpperCase(),
|
|
3572
|
+
rank: Number.isFinite(item.market_cap_rank) ? item.market_cap_rank : null,
|
|
3573
|
+
price: Number.isFinite(price) ? price : null,
|
|
3574
|
+
changePct24h: Number.isFinite(chg) ? chg : null
|
|
3575
|
+
};
|
|
3576
|
+
});
|
|
3577
|
+
});
|
|
3578
|
+
}
|
|
3579
|
+
async getSectorPerformance() {
|
|
3580
|
+
return categoriesCache.get("categories", async () => {
|
|
3581
|
+
const body = await fetchJson(CATEGORIES_URL);
|
|
3582
|
+
if (!Array.isArray(body))
|
|
3583
|
+
throw new Error("coingecko categories: unexpected response shape");
|
|
3584
|
+
return body.filter((c) => Number.isFinite(c.market_cap) && (c.market_cap ?? 0) > 0).map((c) => ({
|
|
3585
|
+
name: c.name,
|
|
3586
|
+
marketCap: c.market_cap,
|
|
3587
|
+
changePct24h: Number.isFinite(c.market_cap_change_24h) ? c.market_cap_change_24h : 0
|
|
3588
|
+
})).sort((a, b) => b.marketCap - a.marketCap).slice(0, 30);
|
|
3589
|
+
});
|
|
3590
|
+
}
|
|
3139
3591
|
async getGlobalMarket() {
|
|
3140
3592
|
return globalCache.get("global", async () => {
|
|
3141
3593
|
const body = await fetchJson(GLOBAL_URL);
|
|
@@ -3169,6 +3621,9 @@ var CHAINS_URL = "https://api.llama.fi/v2/chains";
|
|
|
3169
3621
|
var DEXS_URL = "https://api.llama.fi/overview/dexs";
|
|
3170
3622
|
var FEES_URL = "https://api.llama.fi/overview/fees";
|
|
3171
3623
|
var PROTOCOLS_URL = "https://api.llama.fi/protocols";
|
|
3624
|
+
var STABLES_URL = "https://stablecoins.llama.fi/stablecoins?includePrices=true";
|
|
3625
|
+
var STABLECHAINS_URL = "https://stablecoins.llama.fi/stablecoinchains";
|
|
3626
|
+
var YIELDS_URL = "https://yields.llama.fi/pools";
|
|
3172
3627
|
var SNAPSHOT_TTL_MS = 8 * 6e4;
|
|
3173
3628
|
var HISTORY_TTL_MS = 30 * 6e4;
|
|
3174
3629
|
var tvlCache = new TtlCache({
|
|
@@ -3195,6 +3650,19 @@ var protocolHistoryCache = new TtlCache({
|
|
|
3195
3650
|
namespace: "zframes:defillama:protocol-history",
|
|
3196
3651
|
ttlMs: HISTORY_TTL_MS
|
|
3197
3652
|
});
|
|
3653
|
+
var stablecoinsCache = new TtlCache({
|
|
3654
|
+
namespace: "zframes:defillama:stablecoins",
|
|
3655
|
+
ttlMs: 30 * 6e4,
|
|
3656
|
+
persist: true
|
|
3657
|
+
});
|
|
3658
|
+
var yieldsCache = new TtlCache({
|
|
3659
|
+
namespace: "zframes:defillama:yields",
|
|
3660
|
+
ttlMs: 12 * 6e4
|
|
3661
|
+
});
|
|
3662
|
+
var feesOverviewCache = new TtlCache({
|
|
3663
|
+
namespace: "zframes:defillama:fees-overview",
|
|
3664
|
+
ttlMs: SNAPSHOT_TTL_MS
|
|
3665
|
+
});
|
|
3198
3666
|
var slugKey = (slugs) => [...slugs].sort().join(",");
|
|
3199
3667
|
function toSeries(chart) {
|
|
3200
3668
|
if (!Array.isArray(chart)) return [];
|
|
@@ -3207,7 +3675,10 @@ var DefiLlamaProvider = class {
|
|
|
3207
3675
|
"tvl",
|
|
3208
3676
|
"dex-volume",
|
|
3209
3677
|
"protocol-tvl",
|
|
3210
|
-
"protocol-fees"
|
|
3678
|
+
"protocol-fees",
|
|
3679
|
+
"stablecoins",
|
|
3680
|
+
"yields",
|
|
3681
|
+
"fees-overview"
|
|
3211
3682
|
];
|
|
3212
3683
|
async getTvlByChain() {
|
|
3213
3684
|
return tvlCache.get("chains", async () => {
|
|
@@ -3292,11 +3763,95 @@ var DefiLlamaProvider = class {
|
|
|
3292
3763
|
})).sort((a, b) => b.fees24h - a.fees24h);
|
|
3293
3764
|
});
|
|
3294
3765
|
}
|
|
3766
|
+
async getStablecoinSupply() {
|
|
3767
|
+
return stablecoinsCache.get("supply", async () => {
|
|
3768
|
+
const [assetsBody, chains] = await Promise.all([
|
|
3769
|
+
fetchJson(STABLES_URL),
|
|
3770
|
+
fetchJson(STABLECHAINS_URL).catch(() => [])
|
|
3771
|
+
]);
|
|
3772
|
+
const assets = assetsBody?.peggedAssets;
|
|
3773
|
+
if (!Array.isArray(assets))
|
|
3774
|
+
throw new Error("defillama stablecoins: unexpected response shape");
|
|
3775
|
+
let now = 0;
|
|
3776
|
+
let d1 = 0;
|
|
3777
|
+
let d7 = 0;
|
|
3778
|
+
let d30 = 0;
|
|
3779
|
+
for (const a of assets) {
|
|
3780
|
+
if (a.pegType && a.pegType !== "peggedUSD") continue;
|
|
3781
|
+
now += a.circulating?.peggedUSD ?? 0;
|
|
3782
|
+
d1 += a.circulatingPrevDay?.peggedUSD ?? 0;
|
|
3783
|
+
d7 += a.circulatingPrevWeek?.peggedUSD ?? 0;
|
|
3784
|
+
d30 += a.circulatingPrevMonth?.peggedUSD ?? 0;
|
|
3785
|
+
}
|
|
3786
|
+
if (now <= 0) throw new Error("defillama stablecoins: empty aggregate");
|
|
3787
|
+
const pct = (prev) => prev > 0 ? (now - prev) / prev * 100 : 0;
|
|
3788
|
+
const nowMs = Date.now();
|
|
3789
|
+
const history = [
|
|
3790
|
+
{ time: nowMs - 30 * 864e5, value: d30 },
|
|
3791
|
+
{ time: nowMs - 7 * 864e5, value: d7 },
|
|
3792
|
+
{ time: nowMs - 864e5, value: d1 },
|
|
3793
|
+
{ time: nowMs, value: now }
|
|
3794
|
+
].filter((p) => p.value > 0);
|
|
3795
|
+
const topChains = (Array.isArray(chains) ? chains : []).map((c) => ({
|
|
3796
|
+
name: c.name,
|
|
3797
|
+
usd: c.totalCirculatingUSD?.peggedUSD ?? 0
|
|
3798
|
+
})).filter((c) => c.usd > 0).sort((a, b) => b.usd - a.usd).slice(0, 12);
|
|
3799
|
+
return {
|
|
3800
|
+
totalUsd: now,
|
|
3801
|
+
changePct1d: pct(d1),
|
|
3802
|
+
changePct7d: pct(d7),
|
|
3803
|
+
changePct30d: pct(d30),
|
|
3804
|
+
history,
|
|
3805
|
+
topChains
|
|
3806
|
+
};
|
|
3807
|
+
});
|
|
3808
|
+
}
|
|
3809
|
+
async getYieldPools() {
|
|
3810
|
+
return yieldsCache.get("pools", async () => {
|
|
3811
|
+
const body = await fetchJson(YIELDS_URL);
|
|
3812
|
+
const data = body?.data;
|
|
3813
|
+
if (!Array.isArray(data))
|
|
3814
|
+
throw new Error("defillama yields: unexpected response shape");
|
|
3815
|
+
return data.filter(
|
|
3816
|
+
(p) => Number.isFinite(p.tvlUsd) && (p.tvlUsd ?? 0) > 0 && Number.isFinite(p.apy)
|
|
3817
|
+
).map((p) => ({
|
|
3818
|
+
pool: p.pool,
|
|
3819
|
+
chain: p.chain,
|
|
3820
|
+
project: p.project,
|
|
3821
|
+
symbol: p.symbol,
|
|
3822
|
+
tvlUsd: p.tvlUsd,
|
|
3823
|
+
apy: p.apy,
|
|
3824
|
+
apyBase: Number.isFinite(p.apyBase) ? p.apyBase : null,
|
|
3825
|
+
apyReward: Number.isFinite(p.apyReward) ? p.apyReward : null,
|
|
3826
|
+
apyPct7D: Number.isFinite(p.apyPct7D) ? p.apyPct7D : null,
|
|
3827
|
+
stablecoin: !!p.stablecoin,
|
|
3828
|
+
ilRisk: p.ilRisk ?? "unknown"
|
|
3829
|
+
})).sort((a, b) => b.tvlUsd - a.tvlUsd).slice(0, 250);
|
|
3830
|
+
});
|
|
3831
|
+
}
|
|
3832
|
+
async getFeesOverview() {
|
|
3833
|
+
return feesOverviewCache.get("overview", async () => {
|
|
3834
|
+
const body = await fetchJson(FEES_URL);
|
|
3835
|
+
if (!body || !Number.isFinite(body.total24h))
|
|
3836
|
+
throw new Error("defillama fees-overview: unexpected response shape");
|
|
3837
|
+
return {
|
|
3838
|
+
total24h: body.total24h,
|
|
3839
|
+
total7d: Number.isFinite(body.total7d) ? body.total7d : null,
|
|
3840
|
+
changePct: Number.isFinite(body.change_1d) ? body.change_1d : null,
|
|
3841
|
+
history: toSeries(body.totalDataChart)
|
|
3842
|
+
};
|
|
3843
|
+
});
|
|
3844
|
+
}
|
|
3295
3845
|
};
|
|
3296
3846
|
|
|
3297
3847
|
// ../provider-hyperliquid/src/index.ts
|
|
3298
3848
|
var WS_URL = "wss://api.hyperliquid.xyz/ws";
|
|
3299
3849
|
var INFO_URL = "https://api.hyperliquid.xyz/info";
|
|
3850
|
+
var VENUE_LABELS = {
|
|
3851
|
+
HlPerp: "Hyperliquid",
|
|
3852
|
+
BinPerp: "Binance",
|
|
3853
|
+
BybitPerp: "Bybit"
|
|
3854
|
+
};
|
|
3300
3855
|
var dexOf = (symbol) => symbol.includes(":") ? symbol.split(":")[0] : "";
|
|
3301
3856
|
async function info(body) {
|
|
3302
3857
|
return fetchJson(INFO_URL, void 0, {
|
|
@@ -3325,6 +3880,10 @@ var fundingCache = new TtlCache({
|
|
|
3325
3880
|
ttlMs: 4.5 * 6e4,
|
|
3326
3881
|
persist: true
|
|
3327
3882
|
});
|
|
3883
|
+
var fundingComparisonCache = new TtlCache({
|
|
3884
|
+
namespace: "zframes:hyperliquid:funding-comparison",
|
|
3885
|
+
ttlMs: 5 * 6e4
|
|
3886
|
+
});
|
|
3328
3887
|
var sortedKey = (symbols) => symbols ? [...symbols].sort().join(",") : "*";
|
|
3329
3888
|
var HyperliquidProvider = class {
|
|
3330
3889
|
name = "hyperliquid";
|
|
@@ -3333,8 +3892,48 @@ var HyperliquidProvider = class {
|
|
|
3333
3892
|
"day-stats",
|
|
3334
3893
|
"funding-history",
|
|
3335
3894
|
"ohlcv",
|
|
3336
|
-
"open-interest"
|
|
3895
|
+
"open-interest",
|
|
3896
|
+
"funding-comparison"
|
|
3337
3897
|
];
|
|
3898
|
+
async getFundingComparison() {
|
|
3899
|
+
return fundingComparisonCache.get("all", async () => {
|
|
3900
|
+
const resp = await info({
|
|
3901
|
+
type: "predictedFundings"
|
|
3902
|
+
});
|
|
3903
|
+
if (!Array.isArray(resp))
|
|
3904
|
+
throw new Error("hyperliquid predictedFundings: unexpected shape");
|
|
3905
|
+
const out = [];
|
|
3906
|
+
for (const entry of resp) {
|
|
3907
|
+
if (!Array.isArray(entry) || entry.length < 2) continue;
|
|
3908
|
+
const [coin, venueList] = entry;
|
|
3909
|
+
if (typeof coin !== "string" || !Array.isArray(venueList)) continue;
|
|
3910
|
+
const venues = [];
|
|
3911
|
+
for (const vEntry of venueList) {
|
|
3912
|
+
if (!Array.isArray(vEntry) || vEntry.length < 2) continue;
|
|
3913
|
+
const [venue, meta] = vEntry;
|
|
3914
|
+
if (!meta) continue;
|
|
3915
|
+
const rawRate = parseFloat(meta.fundingRate);
|
|
3916
|
+
if (!Number.isFinite(rawRate)) continue;
|
|
3917
|
+
const reported = Number(meta.fundingIntervalHours);
|
|
3918
|
+
const intervalHours = Number.isFinite(reported) && reported > 0 ? reported : venue === "HlPerp" ? 1 : 8;
|
|
3919
|
+
venues.push({
|
|
3920
|
+
venue: VENUE_LABELS[venue] ?? venue,
|
|
3921
|
+
rawRate,
|
|
3922
|
+
intervalHours,
|
|
3923
|
+
annualizedPct: rawRate * (8760 / intervalHours) * 100
|
|
3924
|
+
});
|
|
3925
|
+
}
|
|
3926
|
+
if (venues.length < 2) continue;
|
|
3927
|
+
const rates = venues.map((v) => v.annualizedPct);
|
|
3928
|
+
out.push({
|
|
3929
|
+
coin,
|
|
3930
|
+
venues,
|
|
3931
|
+
spreadPct: Math.max(...rates) - Math.min(...rates)
|
|
3932
|
+
});
|
|
3933
|
+
}
|
|
3934
|
+
return out.sort((a, b) => Math.abs(b.spreadPct) - Math.abs(a.spreadPct)).slice(0, 80);
|
|
3935
|
+
});
|
|
3936
|
+
}
|
|
3338
3937
|
ws = null;
|
|
3339
3938
|
listeners = /* @__PURE__ */ new Set();
|
|
3340
3939
|
reconnectTimer = null;
|