Skip to content

Commit cec7a03

Browse files
authored
Merge pull request #1005 from pendulum-chain/staging
Create new production release
2 parents bea83d3 + 5233217 commit cec7a03

File tree

26 files changed

+512
-410
lines changed

26 files changed

+512
-410
lines changed

apps/api/src/api/controllers/metrics.controller.ts

Lines changed: 60 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -7,30 +7,38 @@ import { cache } from "../services";
77
const CACHE_TTL_SECONDS = 5 * 60; // 5 minutes
88

99
export interface VolumeRow {
10+
chain: string;
1011
buy_usd: number;
1112
sell_usd: number;
1213
total_usd: number;
1314
}
1415

15-
export interface DailyVolume extends VolumeRow {
16+
export interface MonthlyVolume extends VolumeRow {
17+
month: string;
18+
}
19+
20+
export interface ChainVolume {
21+
chain: string;
22+
buy_usd: number;
23+
sell_usd: number;
24+
total_usd: number;
25+
}
26+
27+
export interface DailyVolume {
1628
day: string;
29+
chains: ChainVolume[];
1730
}
1831

19-
export interface MonthlyVolume extends VolumeRow {
32+
export interface MonthlyVolume {
2033
month: string;
34+
chains: ChainVolume[];
2135
}
2236

23-
export interface WeeklyVolume extends VolumeRow {
37+
export interface WeeklyVolume {
2438
week: string;
2539
startDate: string;
2640
endDate: string;
27-
}
28-
29-
export interface VolumeData {
30-
monthly: MonthlyVolume[];
31-
weekly: WeeklyVolume[];
32-
daily: DailyVolume[];
33-
selectedMonth: string;
41+
chains: ChainVolume[];
3442
}
3543

3644
let supabaseClient: SupabaseClient | null = null;
@@ -50,9 +58,7 @@ function getSupabaseClient() {
5058

5159
const zeroVolume = (key: string, keyName: "day" | "month"): any => ({
5260
[keyName]: key,
53-
buy_usd: 0,
54-
sell_usd: 0,
55-
total_usd: 0
61+
chains: []
5662
});
5763

5864
async function getMonthlyVolumes(): Promise<MonthlyVolume[]> {
@@ -62,7 +68,7 @@ async function getMonthlyVolumes(): Promise<MonthlyVolume[]> {
6268

6369
try {
6470
const supabase = getSupabaseClient();
65-
const { data, error } = await supabase.rpc("get_monthly_volumes", { year_param: null });
71+
const { data, error } = await supabase.rpc("get_monthly_volumes_by_chain", { year_param: null });
6672
if (error) throw error;
6773

6874
const rawData = (data as MonthlyVolume[]) || [];
@@ -91,60 +97,58 @@ async function getMonthlyVolumes(): Promise<MonthlyVolume[]> {
9197
}
9298

9399
async function getDailyVolumes(startDate: string, endDate: string): Promise<DailyVolume[]> {
94-
const cacheKey = `daily-${startDate}-${endDate}`;
95-
const cached = cache.get<DailyVolume[]>(cacheKey);
96-
if (cached) return cached;
97-
98-
try {
99-
const supabase = getSupabaseClient();
100-
const { data, error } = await supabase.rpc("get_daily_volumes", { end_date: endDate, start_date: startDate });
101-
if (error) throw error;
102-
103-
const rawData = (data as DailyVolume[]) || [];
104-
const dataMap = new Map(rawData.map(row => [row.day, row]));
105-
106-
const current = new Date(startDate);
107-
const end = new Date(endDate);
108-
const volumes: DailyVolume[] = [];
109-
110-
while (current <= end) {
111-
const dayStr = current.toISOString().slice(0, 10);
112-
volumes.push(dataMap.get(dayStr) || zeroVolume(dayStr, "day"));
113-
current.setDate(current.getDate() + 1);
114-
}
115-
116-
cache.set(cacheKey, volumes, CACHE_TTL_SECONDS);
117-
return volumes;
118-
} catch (error: any) {
119-
throw new Error("Could not calculate daily volumes: " + error.message);
100+
const supabase = getSupabaseClient();
101+
const { data, error } = await supabase.rpc("get_daily_volumes_by_chain", {
102+
end_date: endDate,
103+
start_date: startDate
104+
});
105+
106+
if (error) throw error;
107+
108+
const rawData = (data as DailyVolume[]) || [];
109+
const dataMap = new Map(rawData.map(row => [row.day, row]));
110+
111+
const current = new Date(startDate);
112+
const end = new Date(endDate);
113+
const volumes: DailyVolume[] = [];
114+
115+
while (current <= end) {
116+
const dayStr = current.toISOString().slice(0, 10);
117+
// If date is missing, return empty chains array instead of zeroed fields
118+
volumes.push(dataMap.get(dayStr) || { chains: [], day: dayStr });
119+
current.setDate(current.getDate() + 1);
120120
}
121+
122+
return volumes;
121123
}
122124

123125
function aggregateWeekly(daily: DailyVolume[]): WeeklyVolume[] {
124126
const weeks: WeeklyVolume[] = [];
125127

126128
for (let i = 0; i < daily.length; i += 7) {
127129
const chunk = daily.slice(i, i + 7);
128-
const startDay = chunk[0];
129-
const endDay = chunk[chunk.length - 1];
130-
131-
const startDate = new Date(startDay.day);
132-
const endDate = new Date(endDay.day);
133-
134-
const startMonth = startDate.toLocaleString("en-US", { month: "short", timeZone: "UTC" });
135-
const endMonth = endDate.toLocaleString("en-US", { month: "short", timeZone: "UTC" });
136-
const weekLabel = `${startMonth} ${startDate.getUTCDate()} - ${endMonth} ${endDate.getUTCDate()}`;
130+
const startDay = chunk[0].day;
131+
const endDay = chunk[chunk.length - 1].day;
132+
133+
const chainTotals = new Map<string, any>();
134+
135+
chunk.forEach(day => {
136+
day.chains.forEach((c: any) => {
137+
const existing = chainTotals.get(c.chain) || { buy_usd: 0, chain: c.chain, sell_usd: 0, total_usd: 0 };
138+
existing.buy_usd += c.buy_usd;
139+
existing.sell_usd += c.sell_usd;
140+
existing.total_usd += c.total_usd;
141+
chainTotals.set(c.chain, existing);
142+
});
143+
});
137144

138145
weeks.push({
139-
buy_usd: chunk.reduce((sum, d) => sum + d.buy_usd, 0),
140-
endDate: endDay.day,
141-
sell_usd: chunk.reduce((sum, d) => sum + d.sell_usd, 0),
142-
startDate: startDay.day,
143-
total_usd: chunk.reduce((sum, d) => sum + d.total_usd, 0),
144-
week: weekLabel
146+
chains: Array.from(chainTotals.values()),
147+
endDate: endDay,
148+
startDate: startDay,
149+
week: `${startDay} to ${endDay}`
145150
});
146151
}
147-
148152
return weeks;
149153
}
150154

0 commit comments

Comments
 (0)