arbitrage-engine/frontend/lib/api.ts

105 lines
2.4 KiB
TypeScript

const API_BASE = process.env.NEXT_PUBLIC_API_URL ?? "";
export interface RateData {
symbol: string;
markPrice: number;
indexPrice: number;
lastFundingRate: number;
nextFundingTime: number;
timestamp: number;
}
export interface RatesResponse {
BTC: RateData;
ETH: RateData;
}
export interface HistoryPoint {
fundingTime: number;
fundingRate: number;
timestamp: string;
}
export interface HistoryResponse {
BTC: HistoryPoint[];
ETH: HistoryPoint[];
}
export interface AssetStats {
mean7d: number;
annualized: number;
count: number;
}
export interface StatsResponse {
BTC: AssetStats;
ETH: AssetStats;
combo: { mean7d: number; annualized: number };
}
export interface SignalHistoryItem {
id: number;
symbol: string;
rate: number;
annualized: number;
sent_at: string;
message: string;
}
export interface SignalsHistoryResponse {
items: SignalHistoryItem[];
}
export interface SnapshotItem {
ts: number;
btc_rate: number;
eth_rate: number;
btc_price: number;
eth_price: number;
}
export interface SnapshotsResponse {
count: number;
hours: number;
data: SnapshotItem[];
}
export interface KBar {
time: number;
open: number; high: number; low: number; close: number;
price_open: number; price_high: number; price_low: number; price_close: number;
}
export interface KlineResponse {
symbol: string; interval: string; count: number; data: KBar[];
}
export interface YtdStats {
annualized: number;
count: number;
}
export interface YtdStatsResponse {
BTC: YtdStats;
ETH: YtdStats;
}
async function fetchAPI<T>(path: string): Promise<T> {
const res = await fetch(`${API_BASE}${path}`, { cache: "no-store" });
if (!res.ok) throw new Error(`API error ${res.status}`);
return res.json();
}
export const api = {
rates: () => fetchAPI<RatesResponse>("/api/rates"),
history: () => fetchAPI<HistoryResponse>("/api/history"),
stats: () => fetchAPI<StatsResponse>("/api/stats"),
health: () => fetchAPI<{ status: string }>("/api/health"),
signalsHistory: () => fetchAPI<SignalsHistoryResponse>("/api/signals/history"),
snapshots: (hours = 24, limit = 5000) =>
fetchAPI<SnapshotsResponse>(`/api/snapshots?hours=${hours}&limit=${limit}`),
kline: (symbol = "BTC", interval = "1h", limit = 500) =>
fetchAPI<KlineResponse>(`/api/kline?symbol=${symbol}&interval=${interval}&limit=${limit}`),
statsYtd: () => fetchAPI<YtdStatsResponse>("/api/stats/ytd"),
};