Real-Time Market Data & SSE Architecture
📡 Real-Time Market Data & SSE Architecture
Section titled “📡 Real-Time Market Data & SSE Architecture”Delivering real-time cryptocurrency price updates directly to the browser poses distinct engineering challenges:
- Connecting the browser directly to multiple external WebSockets exhausts browser resources, triggers CORS complications, and leaks user portfolio interests to third-party exchanges.
- Polling REST APIs frequently triggers rate-limits (
429 Too Many Requests).
To solve this, Kryptofolio implements a centralized Server-Sent Events (SSE) architecture orchestrated entirely by the Hono backend.
🏛️ Architecture Overview
Section titled “🏛️ Architecture Overview”flowchart TD
subgraph Frontend ["Vue 3 Frontend"]
UI["UI Widgets (Live Price & Portfolio Equity)"]
BffAdapter["BffMarketDataAdapter (EventSource)"]
end
subgraph Backend ["Hono Backend Server"]
SSEEndpoint["GET /api/market/stream (SSE)"]
Orchestrator["MarketDataOrchestrator"]
PriceHistory["IPriceHistoryPort (Cache & Parquet)"]
Provider1["Kraken WS Adapter (Active)"]
Provider2["Binance WS Adapter (Standby)"]
end
subgraph Exchanges ["External Crypto Exchanges"]
KrakenWS["Kraken WebSocket API v2"]
BinanceWS["Binance WebSocket Stream"]
end
UI --> BffAdapter
BffAdapter -->|Single EventSource Connection| SSEEndpoint
SSEEndpoint --> Orchestrator
Orchestrator -->|Hot-swaps active feed| Provider1
Orchestrator -.->|Disabled| Provider2
KrakenWS ==>|Live Ticks| Provider1
Provider1 --> Orchestrator
Orchestrator -->|1. Flush to Cache & History| PriceHistory
Orchestrator -->|2. Broadcast Tick Payload| SSEEndpoint
⚡ Key Architectural Innovations
Section titled “⚡ Key Architectural Innovations”1. The Single Pipe Paradigm
Section titled “1. The Single Pipe Paradigm”The frontend opens exactly one persistent HTTP connection using standard HTML5 EventSource (/api/market/stream). All active asset ticks (e.g. BTC/EUR, ETH/EUR, SOL/USD) travel through this single multiplexed stream.
2. Transparent Hot-Swapping
Section titled “2. Transparent Hot-Swapping”Users can change their preferred market provider in the Settings or Vault view (e.g., switching from Kraken to Binance or CoinGecko):
- The backend
MarketDataOrchestratorcleanly tears down the active Kraken WebSocket session. - It establishes a connection to the newly selected provider.
- It resumes streaming ticks down the existing SSE pipe.
- The frontend requires zero reconnection logic or UI interruption.
3. REST & Historical Synchronization
Section titled “3. REST & Historical Synchronization”Every live price tick broadcast through SSE is concurrently flushed to the backend IPriceHistoryPort:
- Guarantees that subsequent REST calls (
GET /api/metrics/kpis) evaluate portfolios using the exact same price snapshot currently visible in live UI ticker widgets. - Writes partitioned historical ticks to Apache Parquet files on disk for long-term time-series analysis.
📦 Client-Side Composable (useMarketStream)
Section titled “📦 Client-Side Composable (useMarketStream)”The frontend interacts with market data via a Vue composable:
import { useMarketStream } from '@/composables/queries/useMarketStream';
export function useLivePortfolio() { const { isConnected, latestTicks } = useMarketStream();
const btcPrice = computed(() => latestTicks.value['BTC/EUR']?.price);
return { isConnected, btcPrice };}