arbitrage-engine/frontend/lib/api.ts

117 lines
2.8 KiB
TypeScript

import { authFetch } from "./auth";
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;
}
// Public fetch (no auth needed)
async function fetchPublic<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();
}
// Protected fetch (auth required, auto-refresh)
async function fetchProtected<T>(path: string): Promise<T> {
const res = await authFetch(path, { cache: "no-store" });
if (!res.ok) throw new Error(`API error ${res.status}`);
return res.json();
}
export const api = {
// Public
rates: () => fetchPublic<RatesResponse>("/api/rates"),
health: () => fetchPublic<{ status: string }>("/api/health"),
// Protected
history: () => fetchProtected<HistoryResponse>("/api/history"),
stats: () => fetchProtected<StatsResponse>("/api/stats"),
signalsHistory: () => fetchProtected<SignalsHistoryResponse>("/api/signals/history"),
snapshots: (hours = 24, limit = 5000) =>
fetchProtected<SnapshotsResponse>(`/api/snapshots?hours=${hours}&limit=${limit}`),
kline: (symbol = "BTC", interval = "1h", limit = 500) =>
fetchProtected<KlineResponse>(`/api/kline?symbol=${symbol}&interval=${interval}&limit=${limit}`),
statsYtd: () => fetchProtected<YtdStatsResponse>("/api/stats/ytd"),
};