mirror of
https://github.com/bitcoinresearchkit/brk.git
synced 2026-07-14 20:48:12 -07:00
global: MASSIVE snapshot
This commit is contained in:
@@ -310,11 +310,11 @@ export function createChart({ parent, brk, fitContent }) {
|
||||
|
||||
/** @type {Partial<Record<ChartableIndex, number>>} */
|
||||
const minBarSpacingByIndex = {
|
||||
monthindex: 1,
|
||||
quarterindex: 2,
|
||||
semesterindex: 3,
|
||||
yearindex: 6,
|
||||
decadeindex: 60,
|
||||
month1: 1,
|
||||
month3: 2,
|
||||
month6: 3,
|
||||
year1: 6,
|
||||
year10: 60,
|
||||
};
|
||||
|
||||
/** @param {ChartableIndex} index */
|
||||
@@ -670,7 +670,7 @@ export function createChart({ parent, brk, fitContent }) {
|
||||
ichart.timeScale().fitContent();
|
||||
} else if (
|
||||
(minBarSpacingByIndex[idx] ?? 0) >=
|
||||
/** @type {number} */ (minBarSpacingByIndex.quarterindex)
|
||||
/** @type {number} */ (minBarSpacingByIndex.month3)
|
||||
) {
|
||||
ichart
|
||||
.timeScale()
|
||||
|
||||
@@ -372,14 +372,14 @@ export function createActivitySection({
|
||||
defaultActive: false,
|
||||
}),
|
||||
line({
|
||||
metric: tree.activity.sent14dEma.bitcoin,
|
||||
metric: tree.activity.sent14dEma.btc,
|
||||
name: "14d EMA",
|
||||
color: colors.indicator.main,
|
||||
unit: Unit.btc,
|
||||
defaultActive: false,
|
||||
}),
|
||||
line({
|
||||
metric: tree.activity.sent14dEma.dollars,
|
||||
metric: tree.activity.sent14dEma.usd,
|
||||
name: "14d EMA",
|
||||
color: colors.indicator.main,
|
||||
unit: Unit.usd,
|
||||
@@ -392,13 +392,13 @@ export function createActivitySection({
|
||||
unit: Unit.sats,
|
||||
}),
|
||||
line({
|
||||
metric: tree.activity.sent.bitcoin.sum,
|
||||
metric: tree.activity.sent.btc.sum,
|
||||
name: "sum",
|
||||
color,
|
||||
unit: Unit.btc,
|
||||
}),
|
||||
line({
|
||||
metric: tree.activity.sent.dollars.sum,
|
||||
metric: tree.activity.sent.usd.sum,
|
||||
name: "sum",
|
||||
color,
|
||||
unit: Unit.usd,
|
||||
@@ -416,13 +416,13 @@ export function createActivitySection({
|
||||
unit: Unit.sats,
|
||||
}),
|
||||
line({
|
||||
metric: tree.activity.sent.bitcoin.cumulative,
|
||||
metric: tree.activity.sent.btc.cumulative,
|
||||
name: "all-time",
|
||||
color,
|
||||
unit: Unit.btc,
|
||||
}),
|
||||
line({
|
||||
metric: tree.activity.sent.dollars.cumulative,
|
||||
metric: tree.activity.sent.usd.cumulative,
|
||||
name: "all-time",
|
||||
color,
|
||||
unit: Unit.usd,
|
||||
@@ -689,8 +689,8 @@ export function createGroupedActivitySection({
|
||||
satsBtcUsd({
|
||||
pattern: {
|
||||
sats: tree.activity.sent.sats.sum,
|
||||
bitcoin: tree.activity.sent.bitcoin.sum,
|
||||
dollars: tree.activity.sent.dollars.sum,
|
||||
btc: tree.activity.sent.btc.sum,
|
||||
usd: tree.activity.sent.usd.sum,
|
||||
},
|
||||
name,
|
||||
color,
|
||||
|
||||
@@ -127,16 +127,16 @@ export function initOptions() {
|
||||
throw new Error(`Blueprint has undefined metric: ${blueprint.title}`);
|
||||
}
|
||||
|
||||
// Check for price pattern blueprint (has dollars/sats sub-metrics)
|
||||
// Check for price pattern blueprint (has usd/sats sub-metrics)
|
||||
// Use unknown cast for safe property access check
|
||||
const maybePriceMetric =
|
||||
/** @type {{ dollars?: AnyMetricPattern, sats?: AnyMetricPattern }} */ (
|
||||
/** @type {{ usd?: AnyMetricPattern, sats?: AnyMetricPattern }} */ (
|
||||
/** @type {unknown} */ (blueprint.metric)
|
||||
);
|
||||
if (maybePriceMetric.dollars?.by && maybePriceMetric.sats?.by) {
|
||||
const { dollars, sats } = maybePriceMetric;
|
||||
if (maybePriceMetric.usd?.by && maybePriceMetric.sats?.by) {
|
||||
const { usd, sats } = maybePriceMetric;
|
||||
if (!usdArr) map.set(Unit.usd, (usdArr = []));
|
||||
usdArr.push({ ...blueprint, metric: dollars, unit: Unit.usd });
|
||||
usdArr.push({ ...blueprint, metric: usd, unit: Unit.usd });
|
||||
|
||||
if (!satsArr) map.set(Unit.sats, (satsArr = []));
|
||||
satsArr.push({ ...blueprint, metric: sats, unit: Unit.sats });
|
||||
|
||||
@@ -5,7 +5,7 @@ import { brk } from "../client.js";
|
||||
import { includes } from "../utils/array.js";
|
||||
import { Unit } from "../utils/units.js";
|
||||
import { priceLine, priceLines } from "./constants.js";
|
||||
import { baseline, candlestick, histogram, line, price } from "./series.js";
|
||||
import { baseline, histogram, line, price } from "./series.js";
|
||||
import { createPriceRatioCharts } from "./shared.js";
|
||||
import { periodIdToName } from "./utils.js";
|
||||
|
||||
@@ -184,7 +184,7 @@ function historicalSubSection(name, periods) {
|
||||
* @returns {PartialOptionsGroup}
|
||||
*/
|
||||
export function createMarketSection() {
|
||||
const { market, supply, distribution, price: priceMetrics } = brk.metrics;
|
||||
const { market, supply, distribution, prices } = brk.metrics;
|
||||
const {
|
||||
movingAverage: ma,
|
||||
ath,
|
||||
@@ -265,8 +265,7 @@ export function createMarketSection() {
|
||||
},
|
||||
];
|
||||
|
||||
const totalReturnPeriods =
|
||||
shortPeriodsBase.length + longPeriodsBase.length;
|
||||
const totalReturnPeriods = shortPeriodsBase.length + longPeriodsBase.length;
|
||||
|
||||
/** @type {Period[]} */
|
||||
const shortPeriods = shortPeriodsBase.map((p, i) => ({
|
||||
@@ -364,25 +363,13 @@ export function createMarketSection() {
|
||||
name: "Market",
|
||||
tree: [
|
||||
{ name: "Price", title: "Bitcoin Price" },
|
||||
{
|
||||
name: "Oracle",
|
||||
title: "On-chain Price",
|
||||
top: [
|
||||
// @ts-ignore
|
||||
candlestick({
|
||||
metric: priceMetrics.oracle.ohlcDollars,
|
||||
name: "Oracle",
|
||||
unit: Unit.usd,
|
||||
}),
|
||||
],
|
||||
},
|
||||
|
||||
{
|
||||
name: "Sats/$",
|
||||
title: "Sats per Dollar",
|
||||
bottom: [
|
||||
line({
|
||||
metric: priceMetrics.sats.split.close,
|
||||
metric: prices.sats.split.close,
|
||||
name: "Sats/$",
|
||||
unit: Unit.sats,
|
||||
}),
|
||||
@@ -687,20 +674,20 @@ export function createMarketSection() {
|
||||
title: "RSI (14d)",
|
||||
bottom: [
|
||||
line({
|
||||
metric: indicators.rsi14d,
|
||||
metric: indicators.rsi._1d.rsi,
|
||||
name: "RSI",
|
||||
color: colors.indicator.main,
|
||||
unit: Unit.index,
|
||||
}),
|
||||
line({
|
||||
metric: indicators.rsi14dMax,
|
||||
metric: indicators.rsi._1d.rsiMax,
|
||||
name: "Max",
|
||||
color: colors.stat.max,
|
||||
defaultActive: false,
|
||||
unit: Unit.index,
|
||||
}),
|
||||
line({
|
||||
metric: indicators.rsi14dMin,
|
||||
metric: indicators.rsi._1d.rsiMin,
|
||||
name: "Min",
|
||||
color: colors.stat.min,
|
||||
defaultActive: false,
|
||||
@@ -716,13 +703,13 @@ export function createMarketSection() {
|
||||
title: "Stochastic RSI",
|
||||
bottom: [
|
||||
line({
|
||||
metric: indicators.stochRsiK,
|
||||
metric: indicators.rsi._1d.stochRsiK,
|
||||
name: "K",
|
||||
color: colors.indicator.fast,
|
||||
unit: Unit.index,
|
||||
}),
|
||||
line({
|
||||
metric: indicators.stochRsiD,
|
||||
metric: indicators.rsi._1d.stochRsiD,
|
||||
name: "D",
|
||||
color: colors.indicator.slow,
|
||||
unit: Unit.index,
|
||||
@@ -735,19 +722,19 @@ export function createMarketSection() {
|
||||
title: "MACD",
|
||||
bottom: [
|
||||
line({
|
||||
metric: indicators.macdLine,
|
||||
metric: indicators.macd._1d.line,
|
||||
name: "MACD",
|
||||
color: colors.indicator.fast,
|
||||
unit: Unit.usd,
|
||||
}),
|
||||
line({
|
||||
metric: indicators.macdSignal,
|
||||
metric: indicators.macd._1d.signal,
|
||||
name: "Signal",
|
||||
color: colors.indicator.slow,
|
||||
unit: Unit.usd,
|
||||
}),
|
||||
histogram({
|
||||
metric: indicators.macdHistogram,
|
||||
metric: indicators.macd._1d.histogram,
|
||||
name: "Histogram",
|
||||
unit: Unit.usd,
|
||||
}),
|
||||
|
||||
@@ -53,7 +53,7 @@ const ANTPOOL_AND_FRIENDS_IDS = /** @type {const} */ ([
|
||||
* @returns {PartialOptionsGroup}
|
||||
*/
|
||||
export function createMiningSection() {
|
||||
const { blocks, transactions, pools } = brk.metrics;
|
||||
const { blocks, transactions, pools, mining } = brk.metrics;
|
||||
|
||||
// Pre-compute pool entries with resolved names
|
||||
const poolData = entries(pools.vecs).map(([id, pool]) => ({
|
||||
@@ -223,33 +223,33 @@ export function createMiningSection() {
|
||||
title: "Network Hashrate",
|
||||
bottom: [
|
||||
dots({
|
||||
metric: blocks.mining.hashRate,
|
||||
metric: mining.hashrate.hashRate,
|
||||
name: "Hashrate",
|
||||
unit: Unit.hashRate,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashRate1wSma,
|
||||
metric: mining.hashrate.hashRate1wSma,
|
||||
name: "1w SMA",
|
||||
color: colors.time._1w,
|
||||
unit: Unit.hashRate,
|
||||
defaultActive: false,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashRate1mSma,
|
||||
metric: mining.hashrate.hashRate1mSma,
|
||||
name: "1m SMA",
|
||||
color: colors.time._1m,
|
||||
unit: Unit.hashRate,
|
||||
defaultActive: false,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashRate2mSma,
|
||||
metric: mining.hashrate.hashRate2mSma,
|
||||
name: "2m SMA",
|
||||
color: colors.indicator.main,
|
||||
unit: Unit.hashRate,
|
||||
defaultActive: false,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashRate1ySma,
|
||||
metric: mining.hashrate.hashRate1ySma,
|
||||
name: "1y SMA",
|
||||
color: colors.time._1y,
|
||||
unit: Unit.hashRate,
|
||||
@@ -262,7 +262,7 @@ export function createMiningSection() {
|
||||
unit: Unit.hashRate,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashRateAth,
|
||||
metric: mining.hashrate.hashRateAth,
|
||||
name: "ATH",
|
||||
color: colors.loss,
|
||||
unit: Unit.hashRate,
|
||||
@@ -275,13 +275,13 @@ export function createMiningSection() {
|
||||
title: "Network Hashrate ATH",
|
||||
bottom: [
|
||||
line({
|
||||
metric: blocks.mining.hashRateAth,
|
||||
metric: mining.hashrate.hashRateAth,
|
||||
name: "ATH",
|
||||
color: colors.loss,
|
||||
unit: Unit.hashRate,
|
||||
}),
|
||||
dots({
|
||||
metric: blocks.mining.hashRate,
|
||||
metric: mining.hashrate.hashRate,
|
||||
name: "Hashrate",
|
||||
color: colors.bitcoin,
|
||||
unit: Unit.hashRate,
|
||||
@@ -293,7 +293,7 @@ export function createMiningSection() {
|
||||
title: "Network Hashrate Drawdown",
|
||||
bottom: [
|
||||
line({
|
||||
metric: blocks.mining.hashRateDrawdown,
|
||||
metric: mining.hashrate.hashRateDrawdown,
|
||||
name: "Drawdown",
|
||||
unit: Unit.percentage,
|
||||
color: colors.loss,
|
||||
@@ -370,8 +370,8 @@ export function createMiningSection() {
|
||||
name: "Sum",
|
||||
title: "Revenue Comparison",
|
||||
bottom: revenueBtcSatsUsd({
|
||||
coinbase: blocks.rewards.coinbase,
|
||||
subsidy: blocks.rewards.subsidy,
|
||||
coinbase: mining.rewards.coinbase,
|
||||
subsidy: mining.rewards.subsidy,
|
||||
fee: transactions.fees.fee,
|
||||
key: "sum",
|
||||
}),
|
||||
@@ -380,8 +380,8 @@ export function createMiningSection() {
|
||||
name: "Cumulative",
|
||||
title: "Revenue Comparison (Total)",
|
||||
bottom: revenueBtcSatsUsd({
|
||||
coinbase: blocks.rewards.coinbase,
|
||||
subsidy: blocks.rewards.subsidy,
|
||||
coinbase: mining.rewards.coinbase,
|
||||
subsidy: mining.rewards.subsidy,
|
||||
fee: transactions.fees.fee,
|
||||
key: "cumulative",
|
||||
}),
|
||||
@@ -396,17 +396,17 @@ export function createMiningSection() {
|
||||
title: "Coinbase Rewards",
|
||||
bottom: [
|
||||
...satsBtcUsdFromFull({
|
||||
source: blocks.rewards.coinbase,
|
||||
source: mining.rewards.coinbase,
|
||||
key: "base",
|
||||
name: "sum",
|
||||
}),
|
||||
...satsBtcUsdFrom({
|
||||
source: blocks.rewards.coinbase,
|
||||
source: mining.rewards.coinbase,
|
||||
key: "sum",
|
||||
name: "sum",
|
||||
}),
|
||||
...satsBtcUsd({
|
||||
pattern: blocks.rewards._24hCoinbaseSum,
|
||||
pattern: mining.rewards._24hCoinbaseSum,
|
||||
name: "24h",
|
||||
color: colors.time._24h,
|
||||
defaultActive: false,
|
||||
@@ -416,13 +416,13 @@ export function createMiningSection() {
|
||||
{
|
||||
name: "Distribution",
|
||||
title: "Coinbase Rewards per Block Distribution",
|
||||
bottom: distributionBtcSatsUsd(blocks.rewards.coinbase),
|
||||
bottom: distributionBtcSatsUsd(mining.rewards.coinbase),
|
||||
},
|
||||
{
|
||||
name: "Cumulative",
|
||||
title: "Coinbase Rewards (Total)",
|
||||
bottom: satsBtcUsdFrom({
|
||||
source: blocks.rewards.coinbase,
|
||||
source: mining.rewards.coinbase,
|
||||
key: "cumulative",
|
||||
name: "all-time",
|
||||
}),
|
||||
@@ -437,17 +437,17 @@ export function createMiningSection() {
|
||||
title: "Block Subsidy",
|
||||
bottom: [
|
||||
...satsBtcUsdFromFull({
|
||||
source: blocks.rewards.subsidy,
|
||||
source: mining.rewards.subsidy,
|
||||
key: "base",
|
||||
name: "sum",
|
||||
}),
|
||||
...satsBtcUsdFrom({
|
||||
source: blocks.rewards.subsidy,
|
||||
source: mining.rewards.subsidy,
|
||||
key: "sum",
|
||||
name: "sum",
|
||||
}),
|
||||
line({
|
||||
metric: blocks.rewards.subsidyUsd1ySma,
|
||||
metric: mining.rewards.subsidyUsd1ySma,
|
||||
name: "1y SMA",
|
||||
color: colors.time._1y,
|
||||
unit: Unit.usd,
|
||||
@@ -458,13 +458,13 @@ export function createMiningSection() {
|
||||
{
|
||||
name: "Distribution",
|
||||
title: "Block Subsidy Distribution",
|
||||
bottom: distributionBtcSatsUsd(blocks.rewards.subsidy),
|
||||
bottom: distributionBtcSatsUsd(mining.rewards.subsidy),
|
||||
},
|
||||
{
|
||||
name: "Cumulative",
|
||||
title: "Block Subsidy (Total)",
|
||||
bottom: satsBtcUsdFrom({
|
||||
source: blocks.rewards.subsidy,
|
||||
source: mining.rewards.subsidy,
|
||||
key: "cumulative",
|
||||
name: "all-time",
|
||||
}),
|
||||
@@ -504,13 +504,13 @@ export function createMiningSection() {
|
||||
title: "Revenue Dominance",
|
||||
bottom: [
|
||||
line({
|
||||
metric: blocks.rewards.subsidyDominance,
|
||||
metric: mining.rewards.subsidyDominance,
|
||||
name: "Subsidy",
|
||||
color: colors.mining.subsidy,
|
||||
unit: Unit.percentage,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.rewards.feeDominance,
|
||||
metric: mining.rewards.feeDominance24h,
|
||||
name: "Fees",
|
||||
color: colors.mining.fee,
|
||||
unit: Unit.percentage,
|
||||
@@ -524,7 +524,7 @@ export function createMiningSection() {
|
||||
name: "Sum",
|
||||
title: "Unclaimed Rewards",
|
||||
bottom: satsBtcUsdFrom({
|
||||
source: blocks.rewards.unclaimedRewards,
|
||||
source: mining.rewards.unclaimedRewards,
|
||||
key: "sum",
|
||||
name: "sum",
|
||||
}),
|
||||
@@ -533,7 +533,7 @@ export function createMiningSection() {
|
||||
name: "Cumulative",
|
||||
title: "Unclaimed Rewards (Total)",
|
||||
bottom: satsBtcUsdFrom({
|
||||
source: blocks.rewards.unclaimedRewards,
|
||||
source: mining.rewards.unclaimedRewards,
|
||||
key: "cumulative",
|
||||
name: "all-time",
|
||||
}),
|
||||
@@ -552,25 +552,25 @@ export function createMiningSection() {
|
||||
title: "Hash Price",
|
||||
bottom: [
|
||||
line({
|
||||
metric: blocks.mining.hashPriceThs,
|
||||
metric: mining.hashrate.hashPriceThs,
|
||||
name: "TH/s",
|
||||
color: colors.usd,
|
||||
unit: Unit.usdPerThsPerDay,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashPricePhs,
|
||||
metric: mining.hashrate.hashPricePhs,
|
||||
name: "PH/s",
|
||||
color: colors.usd,
|
||||
unit: Unit.usdPerPhsPerDay,
|
||||
}),
|
||||
dotted({
|
||||
metric: blocks.mining.hashPriceThsMin,
|
||||
metric: mining.hashrate.hashPriceThsMin,
|
||||
name: "TH/s Min",
|
||||
color: colors.stat.min,
|
||||
unit: Unit.usdPerThsPerDay,
|
||||
}),
|
||||
dotted({
|
||||
metric: blocks.mining.hashPricePhsMin,
|
||||
metric: mining.hashrate.hashPricePhsMin,
|
||||
name: "PH/s Min",
|
||||
color: colors.stat.min,
|
||||
unit: Unit.usdPerPhsPerDay,
|
||||
@@ -582,25 +582,25 @@ export function createMiningSection() {
|
||||
title: "Hash Value",
|
||||
bottom: [
|
||||
line({
|
||||
metric: blocks.mining.hashValueThs,
|
||||
metric: mining.hashrate.hashValueThs,
|
||||
name: "TH/s",
|
||||
color: colors.bitcoin,
|
||||
unit: Unit.satsPerThsPerDay,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashValuePhs,
|
||||
metric: mining.hashrate.hashValuePhs,
|
||||
name: "PH/s",
|
||||
color: colors.bitcoin,
|
||||
unit: Unit.satsPerPhsPerDay,
|
||||
}),
|
||||
dotted({
|
||||
metric: blocks.mining.hashValueThsMin,
|
||||
metric: mining.hashrate.hashValueThsMin,
|
||||
name: "TH/s Min",
|
||||
color: colors.stat.min,
|
||||
unit: Unit.satsPerThsPerDay,
|
||||
}),
|
||||
dotted({
|
||||
metric: blocks.mining.hashValuePhsMin,
|
||||
metric: mining.hashrate.hashValuePhsMin,
|
||||
name: "PH/s Min",
|
||||
color: colors.stat.min,
|
||||
unit: Unit.satsPerPhsPerDay,
|
||||
@@ -612,13 +612,13 @@ export function createMiningSection() {
|
||||
title: "Recovery",
|
||||
bottom: [
|
||||
line({
|
||||
metric: blocks.mining.hashPriceRebound,
|
||||
metric: mining.hashrate.hashPriceRebound,
|
||||
name: "Hash Price",
|
||||
color: colors.usd,
|
||||
unit: Unit.percentage,
|
||||
}),
|
||||
line({
|
||||
metric: blocks.mining.hashValueRebound,
|
||||
metric: mining.hashrate.hashValueRebound,
|
||||
name: "Hash Value",
|
||||
color: colors.bitcoin,
|
||||
unit: Unit.percentage,
|
||||
|
||||
@@ -10,7 +10,7 @@ import { Unit } from "../utils/units.js";
|
||||
/**
|
||||
* Create a price series for the top pane (auto-expands to USD + sats versions)
|
||||
* @param {Object} args
|
||||
* @param {AnyPricePattern} args.metric - Price pattern with dollars and sats
|
||||
* @param {AnyPricePattern} args.metric - Price pattern with usd and sats
|
||||
* @param {string} args.name
|
||||
* @param {string} [args.key]
|
||||
* @param {LineStyle} [args.style]
|
||||
@@ -417,13 +417,13 @@ export function fromStatsPattern({ pattern, unit, title = "" }) {
|
||||
* @returns {AnyFetchedSeriesBlueprint[]}
|
||||
*/
|
||||
export const distributionBtcSatsUsd = (source) => [
|
||||
...fromStatsPattern({ pattern: source.bitcoin, unit: Unit.btc }),
|
||||
...fromStatsPattern({ pattern: source.btc, unit: Unit.btc }),
|
||||
...fromStatsPattern({ pattern: source.sats, unit: Unit.sats }),
|
||||
...fromStatsPattern({ pattern: source.dollars, unit: Unit.usd }),
|
||||
...fromStatsPattern({ pattern: source.usd, unit: Unit.usd }),
|
||||
];
|
||||
|
||||
/**
|
||||
* Create series from a SupplyPattern (sats/bitcoin/dollars, no sum/cumulative)
|
||||
* Create series from a SupplyPattern (sats/btc/usd, no sum/cumulative)
|
||||
* @param {Object} args
|
||||
* @param {SupplyPattern} args.pattern
|
||||
* @param {string} args.title
|
||||
@@ -433,7 +433,7 @@ export const distributionBtcSatsUsd = (source) => [
|
||||
export function fromSupplyPattern({ pattern, title, color }) {
|
||||
return [
|
||||
{
|
||||
metric: pattern.bitcoin,
|
||||
metric: pattern.btc,
|
||||
title,
|
||||
color,
|
||||
unit: Unit.btc,
|
||||
@@ -445,7 +445,7 @@ export function fromSupplyPattern({ pattern, title, color }) {
|
||||
unit: Unit.sats,
|
||||
},
|
||||
{
|
||||
metric: pattern.dollars,
|
||||
metric: pattern.usd,
|
||||
title,
|
||||
color,
|
||||
unit: Unit.usd,
|
||||
@@ -523,7 +523,7 @@ function distributionSeries(pattern, unit) {
|
||||
/**
|
||||
* Create btc/sats/usd series from metrics
|
||||
* @param {Object} args
|
||||
* @param {{ bitcoin: AnyMetricPattern, sats: AnyMetricPattern, dollars: AnyMetricPattern }} args.metrics
|
||||
* @param {{ btc: AnyMetricPattern, sats: AnyMetricPattern, usd: AnyMetricPattern }} args.metrics
|
||||
* @param {string} args.name
|
||||
* @param {Color} [args.color]
|
||||
* @param {boolean} [args.defaultActive]
|
||||
@@ -532,7 +532,7 @@ function distributionSeries(pattern, unit) {
|
||||
function btcSatsUsdSeries({ metrics, name, color, defaultActive }) {
|
||||
return [
|
||||
{
|
||||
metric: metrics.bitcoin,
|
||||
metric: metrics.btc,
|
||||
title: name,
|
||||
color,
|
||||
unit: Unit.btc,
|
||||
@@ -546,7 +546,7 @@ function btcSatsUsdSeries({ metrics, name, color, defaultActive }) {
|
||||
defaultActive,
|
||||
},
|
||||
{
|
||||
metric: metrics.dollars,
|
||||
metric: metrics.usd,
|
||||
title: name,
|
||||
color,
|
||||
unit: Unit.usd,
|
||||
@@ -694,9 +694,9 @@ export function chartsFromValue({ pattern, title, color }) {
|
||||
title,
|
||||
bottom: btcSatsUsdSeries({
|
||||
metrics: {
|
||||
bitcoin: pattern.bitcoin.sum,
|
||||
btc: pattern.btc.sum,
|
||||
sats: pattern.sats.sum,
|
||||
dollars: pattern.dollars.sum,
|
||||
usd: pattern.usd.sum,
|
||||
},
|
||||
name: "sum",
|
||||
color,
|
||||
@@ -707,9 +707,9 @@ export function chartsFromValue({ pattern, title, color }) {
|
||||
title: `${title} (Total)`,
|
||||
bottom: btcSatsUsdSeries({
|
||||
metrics: {
|
||||
bitcoin: pattern.bitcoin.cumulative,
|
||||
btc: pattern.btc.cumulative,
|
||||
sats: pattern.sats.cumulative,
|
||||
dollars: pattern.dollars.cumulative,
|
||||
usd: pattern.usd.cumulative,
|
||||
},
|
||||
name: "all-time",
|
||||
color,
|
||||
@@ -733,17 +733,17 @@ export function chartsFromValueFull({ pattern, title }) {
|
||||
bottom: [
|
||||
...btcSatsUsdSeries({
|
||||
metrics: {
|
||||
bitcoin: pattern.bitcoin.base,
|
||||
btc: pattern.btc.base,
|
||||
sats: pattern.sats.base,
|
||||
dollars: pattern.dollars.base,
|
||||
usd: pattern.usd.base,
|
||||
},
|
||||
name: "sum",
|
||||
}),
|
||||
...btcSatsUsdSeries({
|
||||
metrics: {
|
||||
bitcoin: pattern.bitcoin.sum,
|
||||
btc: pattern.btc.sum,
|
||||
sats: pattern.sats.sum,
|
||||
dollars: pattern.dollars.sum,
|
||||
usd: pattern.usd.sum,
|
||||
},
|
||||
name: "sum",
|
||||
}),
|
||||
@@ -753,9 +753,9 @@ export function chartsFromValueFull({ pattern, title }) {
|
||||
name: "Distribution",
|
||||
title: `${title} Distribution`,
|
||||
bottom: [
|
||||
...distributionSeries(pattern.bitcoin, Unit.btc),
|
||||
...distributionSeries(pattern.btc, Unit.btc),
|
||||
...distributionSeries(pattern.sats, Unit.sats),
|
||||
...distributionSeries(pattern.dollars, Unit.usd),
|
||||
...distributionSeries(pattern.usd, Unit.usd),
|
||||
],
|
||||
},
|
||||
{
|
||||
@@ -763,9 +763,9 @@ export function chartsFromValueFull({ pattern, title }) {
|
||||
title: `${title} (Total)`,
|
||||
bottom: btcSatsUsdSeries({
|
||||
metrics: {
|
||||
bitcoin: pattern.bitcoin.cumulative,
|
||||
btc: pattern.btc.cumulative,
|
||||
sats: pattern.sats.cumulative,
|
||||
dollars: pattern.dollars.cumulative,
|
||||
usd: pattern.usd.cumulative,
|
||||
},
|
||||
name: "all-time",
|
||||
}),
|
||||
|
||||
@@ -72,7 +72,7 @@ export const formatCohortTitle = (cohortTitle) => (metric) =>
|
||||
cohortTitle ? `${metric}: ${cohortTitle}` : metric;
|
||||
|
||||
/**
|
||||
* Create sats/btc/usd line series from a pattern with .sats/.bitcoin/.dollars
|
||||
* Create sats/btc/usd line series from a pattern with .sats/.btc/.usd
|
||||
* @param {Object} args
|
||||
* @param {AnyValuePattern} args.pattern
|
||||
* @param {string} args.name
|
||||
@@ -84,7 +84,7 @@ export const formatCohortTitle = (cohortTitle) => (metric) =>
|
||||
export function satsBtcUsd({ pattern, name, color, defaultActive, style }) {
|
||||
return [
|
||||
line({
|
||||
metric: pattern.bitcoin,
|
||||
metric: pattern.btc,
|
||||
name,
|
||||
color,
|
||||
unit: Unit.btc,
|
||||
@@ -100,7 +100,7 @@ export function satsBtcUsd({ pattern, name, color, defaultActive, style }) {
|
||||
style,
|
||||
}),
|
||||
line({
|
||||
metric: pattern.dollars,
|
||||
metric: pattern.usd,
|
||||
name,
|
||||
color,
|
||||
unit: Unit.usd,
|
||||
@@ -113,7 +113,7 @@ export function satsBtcUsd({ pattern, name, color, defaultActive, style }) {
|
||||
/**
|
||||
* Create sats/btc/usd baseline series from a value pattern
|
||||
* @param {Object} args
|
||||
* @param {{ bitcoin: AnyMetricPattern, sats: AnyMetricPattern, dollars: AnyMetricPattern }} args.pattern
|
||||
* @param {{ btc: AnyMetricPattern, sats: AnyMetricPattern, usd: AnyMetricPattern }} args.pattern
|
||||
* @param {string} args.name
|
||||
* @param {Color} [args.color]
|
||||
* @param {boolean} [args.defaultActive]
|
||||
@@ -122,7 +122,7 @@ export function satsBtcUsd({ pattern, name, color, defaultActive, style }) {
|
||||
export function satsBtcUsdBaseline({ pattern, name, color, defaultActive }) {
|
||||
return [
|
||||
baseline({
|
||||
metric: pattern.bitcoin,
|
||||
metric: pattern.btc,
|
||||
name,
|
||||
color,
|
||||
unit: Unit.btc,
|
||||
@@ -136,7 +136,7 @@ export function satsBtcUsdBaseline({ pattern, name, color, defaultActive }) {
|
||||
defaultActive,
|
||||
}),
|
||||
baseline({
|
||||
metric: pattern.dollars,
|
||||
metric: pattern.usd,
|
||||
name,
|
||||
color,
|
||||
unit: Unit.usd,
|
||||
@@ -158,9 +158,9 @@ export function satsBtcUsdBaseline({ pattern, name, color, defaultActive }) {
|
||||
export function satsBtcUsdFrom({ source, key, name, color, defaultActive }) {
|
||||
return satsBtcUsd({
|
||||
pattern: {
|
||||
bitcoin: source.bitcoin[key],
|
||||
btc: source.btc[key],
|
||||
sats: source.sats[key],
|
||||
dollars: source.dollars[key],
|
||||
usd: source.usd[key],
|
||||
},
|
||||
name,
|
||||
color,
|
||||
@@ -187,9 +187,9 @@ export function satsBtcUsdFromFull({
|
||||
}) {
|
||||
return satsBtcUsd({
|
||||
pattern: {
|
||||
bitcoin: source.bitcoin[key],
|
||||
btc: source.btc[key],
|
||||
sats: source.sats[key],
|
||||
dollars: source.dollars[key],
|
||||
usd: source.usd[key],
|
||||
},
|
||||
name,
|
||||
color,
|
||||
|
||||
@@ -56,13 +56,13 @@
|
||||
* @typedef {DotsBaselineSeriesBlueprint & FetchedAnySeriesOptions} FetchedDotsBaselineSeriesBlueprint
|
||||
* @typedef {AnySeriesBlueprint & FetchedAnySeriesOptions} AnyFetchedSeriesBlueprint
|
||||
*
|
||||
* Any pattern with dollars and sats sub-metrics (auto-expands to USD + sats)
|
||||
* @typedef {{ dollars: AnyMetricPattern, sats: AnyMetricPattern }} AnyPricePattern
|
||||
* Any pattern with usd and sats sub-metrics (auto-expands to USD + sats)
|
||||
* @typedef {{ usd: AnyMetricPattern, sats: AnyMetricPattern }} AnyPricePattern
|
||||
*
|
||||
* Any pattern with sats, bitcoin, and dollars sub-metrics (value patterns like stack)
|
||||
* @typedef {{ sats: AnyMetricPattern, bitcoin: AnyMetricPattern, dollars: AnyMetricPattern }} AnyValuePattern
|
||||
* Any pattern with sats, btc, and usd sub-metrics (value patterns like stack)
|
||||
* @typedef {{ sats: AnyMetricPattern, btc: AnyMetricPattern, usd: AnyMetricPattern }} AnyValuePattern
|
||||
*
|
||||
* Top pane price series - requires a price pattern with dollars/sats, auto-expands to USD + sats
|
||||
* Top pane price series - requires a price pattern with usd/sats, auto-expands to USD + sats
|
||||
* @typedef {{ metric: AnyPricePattern }} FetchedPriceSeriesOptions
|
||||
* @typedef {LineSeriesBlueprint & FetchedPriceSeriesOptions} FetchedPriceSeriesBlueprint
|
||||
*
|
||||
|
||||
@@ -81,11 +81,11 @@ function markUsedBlueprints(map, arr) {
|
||||
const metric = arr[i].metric;
|
||||
if (!metric) continue;
|
||||
const maybePriceMetric =
|
||||
/** @type {{ dollars?: AnyMetricPattern, sats?: AnyMetricPattern }} */ (
|
||||
/** @type {{ usd?: AnyMetricPattern, sats?: AnyMetricPattern }} */ (
|
||||
/** @type {unknown} */ (metric)
|
||||
);
|
||||
if (maybePriceMetric.dollars?.by && maybePriceMetric.sats?.by) {
|
||||
map.delete(maybePriceMetric.dollars);
|
||||
if (maybePriceMetric.usd?.by && maybePriceMetric.sats?.by) {
|
||||
map.delete(maybePriceMetric.usd);
|
||||
map.delete(maybePriceMetric.sats);
|
||||
} else {
|
||||
map.delete(/** @type {AnyMetricPattern} */ (metric));
|
||||
@@ -145,7 +145,7 @@ export function extractTreeStructure(options) {
|
||||
const grouped = {};
|
||||
for (const s of series) {
|
||||
const metric = /** @type {any} */ (s.metric);
|
||||
if (isTop && metric?.dollars && metric?.sats) {
|
||||
if (isTop && metric?.usd && metric?.sats) {
|
||||
const title = s.title || s.key || "unnamed";
|
||||
(grouped["USD"] ??= []).push(title);
|
||||
(grouped["sats"] ??= []).push(title);
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -45,7 +45,7 @@ export function init() {
|
||||
const usdPrice = {
|
||||
type: "Candlestick",
|
||||
title: "Price",
|
||||
metric: brk.metrics.price.usd.ohlc,
|
||||
metric: brk.metrics.prices.usd.ohlc,
|
||||
};
|
||||
result.set(Unit.usd, [usdPrice, ...(optionTop.get(Unit.usd) ?? [])]);
|
||||
|
||||
@@ -54,7 +54,7 @@ export function init() {
|
||||
const satsPrice = {
|
||||
type: "Candlestick",
|
||||
title: "Price",
|
||||
metric: brk.metrics.price.sats.ohlc,
|
||||
metric: brk.metrics.prices.sats.ohlc,
|
||||
colors: /** @type {const} */ ([colors.bi.p1[1], colors.bi.p1[0]]),
|
||||
};
|
||||
result.set(Unit.sats, [satsPrice, ...(optionTop.get(Unit.sats) ?? [])]);
|
||||
@@ -109,10 +109,10 @@ const ALL_CHOICES = /** @satisfies {ChartableIndexName[]} */ ([
|
||||
"date",
|
||||
"week",
|
||||
"month",
|
||||
"quarter",
|
||||
"semester",
|
||||
"month3",
|
||||
"month6",
|
||||
"year",
|
||||
"decade",
|
||||
"year10",
|
||||
]);
|
||||
|
||||
/**
|
||||
|
||||
+12
-12
@@ -36,7 +36,7 @@
|
||||
* @typedef {Brk.MetricsTree_Distribution_UtxoCohorts_Term_Short} ShortTermPattern
|
||||
* @typedef {Brk.MetricsTree_Distribution_UtxoCohorts_Term_Long} LongTermPattern
|
||||
* @typedef {Brk.MetricsTree_Distribution_UtxoCohorts_All_Relative} AllRelativePattern
|
||||
* @typedef {Brk.MetricsTree_Supply_Circulating} SupplyPattern
|
||||
* @typedef {Brk.BtcSatsUsdPattern} SupplyPattern
|
||||
* @typedef {Brk.MetricsTree_Blocks_Size} BlockSizePattern
|
||||
* @typedef {keyof Brk.MetricsTree_Distribution_UtxoCohorts_Type} SpendableType
|
||||
* @typedef {keyof Brk.MetricsTree_Distribution_AnyAddressIndexes} AddressableType
|
||||
@@ -53,22 +53,22 @@
|
||||
* @typedef {Brk.ActivityCostOutputsRealizedSupplyUnrealizedPattern} EmptyPattern
|
||||
* @typedef {Brk._0sdM0M1M1sdM2M2sdM3sdP0P1P1sdP2P2sdP3sdSdSmaZscorePattern} Ratio1ySdPattern
|
||||
* @typedef {Brk.Dollars} Dollars
|
||||
* CoinbasePattern: patterns with bitcoin/sats/dollars each having fullness + sum + cumulative
|
||||
* @typedef {Brk.BitcoinDollarsSatsPattern2} CoinbasePattern
|
||||
* CoinbasePattern: patterns with btc/sats/usd each having base + sum + cumulative + stats
|
||||
* @typedef {Brk.BtcSatsUsdPattern4} CoinbasePattern
|
||||
* ActivePriceRatioPattern: ratio pattern with price (extended)
|
||||
* @typedef {Brk.PriceRatioPattern} ActivePriceRatioPattern
|
||||
* AnyRatioPattern: full ratio patterns (with or without price) - has ratio, percentiles, z-scores
|
||||
* @typedef {Brk.RatioPattern | Brk.PriceRatioPattern} AnyRatioPattern
|
||||
* ValuePattern: patterns with minimal stats (sum, cumulative only) for bitcoin/sats/dollars
|
||||
* @typedef {Brk.BitcoinDollarsSatsPattern6 | Brk.BitcoinDollarsSatsPattern3} ValuePattern
|
||||
* FullValuePattern: patterns with full stats (base, sum, cumulative, average, percentiles) for bitcoin/sats/dollars
|
||||
* @typedef {Brk.BitcoinDollarsSatsPattern2} FullValuePattern
|
||||
* ValuePattern: patterns with minimal stats (sum, cumulative only) for btc/sats/usd
|
||||
* @typedef {Brk.BtcSatsUsdPattern5 | Brk.BtcSatsUsdPattern2} ValuePattern
|
||||
* FullValuePattern: patterns with full stats (base, sum, cumulative, average, percentiles) for btc/sats/usd
|
||||
* @typedef {Brk.BtcSatsUsdPattern4} FullValuePattern
|
||||
* SumValuePattern: patterns with sum stats (sum, cumulative, average, percentiles - no base) for bitcoin/sats/dollars
|
||||
* @typedef {{bitcoin: SumStatsPattern<any>, sats: SumStatsPattern<any>, dollars: SumStatsPattern<any>}} SumValuePattern
|
||||
* @typedef {{btc: SumStatsPattern<any>, sats: SumStatsPattern<any>, usd: SumStatsPattern<any>}} SumValuePattern
|
||||
* AnyValuePatternType: union of all value pattern types
|
||||
* @typedef {ValuePattern | FullValuePattern} AnyValuePatternType
|
||||
* @typedef {Brk.AnyMetricPattern} AnyMetricPattern
|
||||
* @typedef {Brk.DollarsSatsPattern} ActivePricePattern
|
||||
* @typedef {Brk.SatsUsdPattern} ActivePricePattern
|
||||
* @typedef {Brk.AnyMetricEndpointBuilder} AnyMetricEndpoint
|
||||
* @typedef {Brk.AnyMetricData} AnyMetricData
|
||||
* @typedef {Brk.AllP2aP2pk33P2pk65P2pkhP2shP2trP2wpkhP2wshPattern} AddrCountPattern
|
||||
@@ -110,7 +110,7 @@
|
||||
/**
|
||||
* Full stats pattern: base, average, sum, cumulative, min, max, percentiles
|
||||
* @template T
|
||||
* @typedef {Brk.AverageBaseCumulativeMaxMedianMinPct10Pct25Pct75Pct90SumPattern2<T>} FullStatsPattern
|
||||
* @typedef {Brk.AverageBaseCumulativeMaxMedianMinPct10Pct25Pct75Pct90SumPattern<T>} FullStatsPattern
|
||||
*/
|
||||
/**
|
||||
* Sum stats pattern: average, sum, cumulative, percentiles (NO base)
|
||||
@@ -140,7 +140,7 @@
|
||||
* @typedef {Brk.MetricsTree_Market_Dca} MarketDca
|
||||
* @typedef {Brk._10y2y3y4y5y6y8yPattern} PeriodCagrPattern
|
||||
* Full stats pattern union (both generic and non-generic variants)
|
||||
* @typedef {Brk.AverageBaseCumulativeMaxMedianMinPct10Pct25Pct75Pct90SumPattern | FullStatsPattern<any>} AnyFullStatsPattern
|
||||
* @typedef {Brk.AverageBaseCumulativeMaxMedianMinPct10Pct25Pct75Pct90SumPattern<any> | FullStatsPattern<any>} AnyFullStatsPattern
|
||||
*
|
||||
* DCA period keys - derived from pattern types
|
||||
* @typedef {keyof Brk._10y2y3y4y5y6y8yPattern} LongPeriodKey
|
||||
@@ -205,5 +205,5 @@
|
||||
* @typedef {AnyMetricPattern | Record<string, unknown>} TreeNode
|
||||
*
|
||||
* Chartable index IDs (subset of IndexName that can be charted)
|
||||
* @typedef {"height" | "dateindex" | "weekindex" | "monthindex" | "quarterindex" | "semesterindex" | "yearindex" | "decadeindex"} ChartableIndex
|
||||
* @typedef {"height" | "day1" | "week1" | "month1" | "month3" | "month6" | "year1" | "year10"} ChartableIndex
|
||||
*/
|
||||
|
||||
@@ -18,7 +18,7 @@ export const serdeBool = {
|
||||
};
|
||||
|
||||
/**
|
||||
* @typedef {"timestamp" | "date" | "week" | "month" | "quarter" | "semester" | "year" | "decade"} ChartableIndexName
|
||||
* @typedef {"timestamp" | "date" | "week" | "month" | "month3" | "month6" | "year" | "year10"} ChartableIndexName
|
||||
*/
|
||||
|
||||
export const serdeChartableIndex = {
|
||||
@@ -28,21 +28,21 @@ export const serdeChartableIndex = {
|
||||
*/
|
||||
serialize(v) {
|
||||
switch (v) {
|
||||
case "dateindex":
|
||||
case "day1":
|
||||
return "date";
|
||||
case "decadeindex":
|
||||
return "decade";
|
||||
case "year10":
|
||||
return "year10";
|
||||
case "height":
|
||||
return "timestamp";
|
||||
case "monthindex":
|
||||
case "month1":
|
||||
return "month";
|
||||
case "quarterindex":
|
||||
return "quarter";
|
||||
case "semesterindex":
|
||||
return "semester";
|
||||
case "weekindex":
|
||||
case "month3":
|
||||
return "month3";
|
||||
case "month6":
|
||||
return "month6";
|
||||
case "week1":
|
||||
return "week";
|
||||
case "yearindex":
|
||||
case "year1":
|
||||
return "year";
|
||||
default:
|
||||
return null;
|
||||
@@ -57,19 +57,19 @@ export const serdeChartableIndex = {
|
||||
case "timestamp":
|
||||
return "height";
|
||||
case "date":
|
||||
return "dateindex";
|
||||
return "day1";
|
||||
case "week":
|
||||
return "weekindex";
|
||||
return "week1";
|
||||
case "month":
|
||||
return "monthindex";
|
||||
case "quarter":
|
||||
return "quarterindex";
|
||||
case "semester":
|
||||
return "semesterindex";
|
||||
return "month1";
|
||||
case "month3":
|
||||
return "month3";
|
||||
case "month6":
|
||||
return "month6";
|
||||
case "year":
|
||||
return "yearindex";
|
||||
case "decade":
|
||||
return "decadeindex";
|
||||
return "year1";
|
||||
case "year10":
|
||||
return "year10";
|
||||
default:
|
||||
throw Error("todo");
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user