Skip to content

Latest commit

 

History

History
348 lines (264 loc) · 9.48 KB

File metadata and controls

348 lines (264 loc) · 9.48 KB

Trading Dashboard - Real-Time Stock Exchange UI

A production-ready, real-time trading dashboard frontend built with Next.js 14+, TypeScript, Tailwind CSS, and WebSocket integration. This frontend connects to a Node.js/Express backend with PostgreSQL and Redis for a complete stock exchange simulator.

Tech Stack

  • Next.js 14+ (App Router) - React framework
  • TypeScript - Type-safe development
  • Tailwind CSS v4 - Styling
  • WebSocket API - Real-time updates
  • React Context - State management
  • Fetch API - REST integration

Project Structure

app/
  context/
    AuthContext.tsx        # Authentication context & useAuth hook
  dashboard/
    page.tsx              # Main dashboard page
  login/
    page.tsx              # Login page
  register/
    page.tsx              # Registration page
  layout.tsx              # Root layout with AuthProvider
  page.tsx                # Landing page (redirect)

components/
  DashboardHeader.tsx     # Header with user info & logout
  OrderForm.tsx           # Place buy/sell orders
  OrderBook.tsx           # Real-time order book with bids/asks
  TradeTicker.tsx         # Real-time trade stream (last 20)
  Portfolio.tsx           # Cash balance & positions (auto-refresh)
  OpenOrders.tsx          # Active orders with cancel button

hooks/
  useWebSocket.ts         # Custom WebSocket hook

lib/
  api.ts                  # REST API helpers with auth
  websocket.ts            # Production WebSocket client
  types.ts                # TypeScript interfaces
  auth.ts                 # Auth utilities

proxy.js                  # Route protection (Next.js 16 proxy)
env.example               # Environment variables template

Features

1. Authentication

  • Registration & Login - Create accounts or sign in with email/password
  • JWT Token Management - Secure token storage in localStorage
  • Route Protection - Dashboard requires authentication
  • Auto-Redirect - Logged-in users bypass login page
  • Session Persistence - User stays logged in across page refreshes

2. Real-Time WebSocket Integration

  • Auto-Reconnect - Exponential backoff with max 5 attempts
  • Message Queuing - Queues messages if disconnected
  • Event Subscriptions - Clean subscribe/unsubscribe API
  • Multiple Event Types:
    • orderbook:update - Live bid/ask updates
    • trade:executed - Completed trades
    • order:update - Your order status changes

3. Order Management

  • Place Orders - Buy/Sell with price & quantity
  • Order Validation - Client-side validation before submission
  • Success/Error Messages - User feedback on actions
  • Cancel Orders - One-click cancel on open orders
  • Auto-Refresh - Open orders update every 2 seconds

4. Order Book

  • Top 10 Levels Each Side - Best bids (green) & asks (red)
  • Live Updates - Updates on orderbook:update events
  • Visual Distinction - Color-coded buy/sell sides
  • Hover Effects - Interactive row highlighting

5. Trade Ticker

  • Last 20 Trades - Rolling list of recent executions
  • Live Animation - New trades highlight for 1 second
  • Buy/Sell Colors - Green for buys, red for sells
  • Timestamp Display - Precise execution times

6. Portfolio Management

  • Cash Balance - Available funds display
  • Positions - Holdings by symbol
  • Total Value - Portfolio worth calculation
  • Auto-Refresh - Updates every 5 seconds
  • Position Details - Quantity & average price per position

7. Dashboard Layout

  • Responsive Grid - Adapts from mobile (1 col) → tablet (2 col) → desktop (4 col)
  • Fintech Styling - Dark mode with blue/green/red accents
  • Connection Status - Real-time WebSocket connection indicator
  • Professional UI - Clean, production-ready design

Getting Started

1. Clone & Install

git clone <repo-url>
cd trading-dashboard
npm install

2. Configure Environment

Copy the example and set your backend URLs:

cp env.example .env.local

Edit .env.local:

NEXT_PUBLIC_API_URL=http://localhost:3001
NEXT_PUBLIC_WS_URL=ws://localhost:3001

For production:

NEXT_PUBLIC_API_URL=https://api.exchange.com
NEXT_PUBLIC_WS_URL=wss://api.exchange.com

3. Run Locally

npm run dev

Visit http://localhost:3000 and sign up or login.

API Integration

REST Endpoints

The frontend expects these endpoints on your backend:

Authentication

  • POST /auth/register - Create account

    • Body: { email, password }
    • Response: { token, user: { id, email } }
  • POST /auth/login - Sign in

    • Body: { email, password }
    • Response: { token, user: { id, email } }

Portfolio

  • GET /portfolio - Get user portfolio
    • Auth: JWT header
    • Response: { cash, positions: [{ symbol, quantity, avgPrice }], totalValue }

Orders

  • POST /orders - Place order

    • Auth: JWT header
    • Body: { symbol, side: 'BUY'|'SELL', price, quantity }
    • Response: { id, symbol, side, price, quantity, remainingQuantity, status, createdAt }
  • GET /orders/open - Get open orders

    • Auth: JWT header
    • Response: [{ id, symbol, side, price, quantity, remainingQuantity, status, ... }]
  • DELETE /orders/:id - Cancel order

    • Auth: JWT header
    • Response: {}

WebSocket Events

Subscribe to events via the useWebSocket hook:

const { isConnected, subscribe, send } = useWebSocket(wsUrl);

// Listen for order book updates
const unsub = subscribe('orderbook:update', (data) => {
  console.log('Order book:', data); // { symbol, bids: [...], asks: [...], timestamp }
});

// Listen for new trades
subscribe('trade:executed', (trade) => {
  console.log('Trade:', trade); // { symbol, price, quantity, timestamp, side }
});

// Listen for order updates
subscribe('order:update', (order) => {
  console.log('Order:', order); // { id, symbol, status, remainingQuantity, ... }
});

Authentication Flow

  1. Registration: User fills email/password → calls POST /auth/register
  2. JWT Storage: Token saved to localStorage + API Authorization header
  3. User State: AuthContext stores user info in localStorage
  4. Protected Routes: Proxy redirects unauthenticated users to /login
  5. Logout: Clears localStorage & redirects to /login

Real-Time WebSocket Flow

  1. Connection: useWebSocket hook connects on mount
  2. Auto-Reconnect: Exponential backoff (3s → 6s → 12s → 24s → 48s)
  3. Event Subscriptions: Components subscribe to events
  4. Message Handling: Events trigger callbacks → state updates
  5. Disconnect: Cleanup unsubscribe on unmount

Type Definitions

All types are strictly defined in /lib/types.ts:

interface Order {
  id: string;
  symbol: string;
  side: 'BUY' | 'SELL';
  price: number;
  quantity: number;
  remainingQuantity: number;
  status: string;
}

interface Trade {
  symbol: string;
  price: number;
  quantity: number;
  timestamp: number;
  side?: 'BUY' | 'SELL';
}

interface Portfolio {
  cash: number;
  positions: Position[];
  totalValue?: number;
}

interface OrderBook {
  symbol: string;
  bids: OrderBookLevel[];
  asks: OrderBookLevel[];
  timestamp: number;
}

Deployment

Vercel

npm run build
vercel deploy

Set environment variables in Vercel project settings:

  • NEXT_PUBLIC_API_URL
  • NEXT_PUBLIC_WS_URL

Development

Add a New Component

  1. Create component in /components
  2. Use useWebSocket() for real-time data
  3. Use api.* functions for REST calls
  4. Export from dashboard page

Modify API Calls

  1. Update endpoint in /lib/api.ts
  2. Update types in /lib/types.ts
  3. Update components using that endpoint

Handle Authentication

Use the useAuth() hook anywhere:

import { useAuth } from '@/app/context/AuthContext';

export function MyComponent() {
  const { user, isAuthenticated, logout } = useAuth();
  // ...
}

Error Handling

  • API Errors: Caught and displayed in component error states
  • WebSocket Errors: Connection status shown in dashboard header
  • Auth Errors: Redirect to login on 401 response
  • Network Errors: Graceful fallbacks with "Loading..." states

Performance Optimizations

  • Lazy Loading: Components mount on dashboard page
  • Auto-Refresh: Portfolio (5s), Orders (2s) - configurable intervals
  • Event Debouncing: WebSocket updates trigger state changes
  • CSS Classes: Tailwind for minimal bundle size
  • Production Build: Next.js static optimization

Browser Support

  • Chrome/Edge (latest)
  • Firefox (latest)
  • Safari (latest)
  • Mobile browsers with WebSocket support

Code Quality

  • Strict TypeScript - No any types
  • Clean Components - Separation of concerns
  • Comments - WebSocket flow, auth handling explained
  • Reusable Hooks - useWebSocket, useAuth
  • Error Boundaries - Try-catch in async operations

Troubleshooting

WebSocket Not Connecting

  • Check NEXT_PUBLIC_WS_URL is correct (ws:// for dev, wss:// for prod)
  • Verify backend WebSocket server is running
  • Check browser console for connection logs

API 401 Errors

  • Token expired → user needs to re-login
  • Check localStorage has valid token
  • Verify backend auth endpoint returns correct JWT

Missing Data on Dashboard

  • Wait 5-10 seconds for initial data loads
  • Check Network tab in DevTools for API/WebSocket errors
  • Verify backend endpoints are implemented

Contributing

See ../DEVELOPMENT.md for:

  • Development setup instructions
  • Code style guidelines
  • Testing procedures
  • Deployment guide

License

MIT