3.3 KiB
3.3 KiB
Phase 3: Socket.IO Implementation - Summary
Key Decision: Modify server.js (Option A)
After researching React Router v7 + Socket.IO integration patterns, the recommended approach is:
Why This Approach?
- Industry Standard: Socket.IO requires
http.createServer(app)- this is the documented pattern - Single Port: HTTP and WebSocket traffic on same port (simpler deployment)
- No CORS Issues: Everything runs on same origin
- Works with SSR: Compatible with React Router v7's server-side rendering
- Simpler Deployment: One process, one port, one service
What Changes?
Minimal changes to server.js:
// Before:
app.listen(PORT, () => {...});
// After:
import { createServer } from "http";
const httpServer = createServer(app);
const { initializeSocketIO } = await import("./server/socket.js");
initializeSocketIO(httpServer);
httpServer.listen(PORT, () => {...});
That's it! Just 4 lines changed in server.js.
Alternative Considered: Separate Socket Server (Option B)
Why we rejected this:
- Requires managing two processes
- CORS configuration complexity
- Different ports (3000 for HTTP, 3001 for WebSocket)
- More complex deployment (two services)
- Not the standard pattern
When to use Option B:
- If you absolutely cannot modify server.js
- If you need to scale WebSocket separately from HTTP
- If you're using a microservices architecture
Implementation Steps
Step 1: Create Socket Module
- File:
server/socket.js(not .ts to avoid bundling) - Exports:
initializeSocketIO()andgetSocketIO() - Stores instance globally for route handlers
Step 2: Modify server.js
- Import
http.createServer - Create HTTP server from Express app
- Initialize Socket.IO with HTTP server
- Call
httpServer.listen()instead ofapp.listen()
Step 3: Client Hook
- Create
app/hooks/useDraftSocket.ts - Handles connection/disconnection
- Auto-joins draft room on connect
- Provides
on/offhelpers for events
Step 4: Route Handlers
- Import
getSocketIO()in API routes - Emit events after database writes
- Example: After creating pick, emit
pick-madeto room
Event Architecture
Write Operations → HTTP POST
- Making picks
- Queue management
- Commissioner actions
- Reason: Reliability, error handling, validation
Read Operations → Socket.IO Broadcast
- Pick made notifications
- Timer updates
- Draft status changes
- Reason: Real-time updates to all clients
Testing Checklist
- Server starts with "Socket.IO initialized"
- Browser console shows "Connected to Socket.IO"
- Server logs show "Client connected: [id]"
- Multiple clients can join same draft room
- Picks broadcast to all clients in room
- Disconnection handled gracefully
Production Notes
- Socket.IO auto-upgrades from polling → WebSocket
- Load balancer needs sticky sessions for WebSocket
- Monitor connection counts
- Consider Redis adapter for horizontal scaling (future)
Files Created/Modified
New Files:
server/socket.js- Socket.IO initializationserver/types.d.ts- TypeScript globalsapp/hooks/useDraftSocket.ts- Client hook
Modified Files:
server.js- 4 lines changed (http.createServer)tsconfig.node.json- Add server directory
Total LOC: ~150 lines of new code