import { describe, test, expect, beforeEach, mock } from "bun:test"; import { wsManager } from "../src/lib/server/api"; import type { WebSocket } from "ws"; import type { IncomingMessage } from "http"; describe("WebSocket API", () => { let manager: typeof wsManager; let mockWs: Partial; let mockRequest: Partial; beforeEach(() => { manager = wsManager; mockWs = { readyState: 1, OPEN: 1, send: mock((_data: string) => {}), on: mock((_event: string, _handler: (...args: unknown[]) => void) => {}), close: mock(() => {}), }; mockRequest = { headers: {}, url: "/", }; }); test("handles new connection", () => { manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); expect(mockWs.send).toHaveBeenCalled(); const sentData = (mockWs.send as ReturnType).mock .calls[0][0] as string; const message = JSON.parse(sentData); expect(message.type).toBe("status"); expect(message.payload.connected).toBe(true); }); test("registers event handlers", () => { manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); expect(mockWs.on).toHaveBeenCalledWith("message", expect.any(Function)); expect(mockWs.on).toHaveBeenCalledWith("close", expect.any(Function)); expect(mockWs.on).toHaveBeenCalledWith("error", expect.any(Function)); }); test("handles authentication message", async () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); const authMessage = JSON.stringify({ type: "auth", payload: { token: "test-token" }, timestamp: Date.now(), }); await handlers["message"](authMessage); expect(mockWs.send).toHaveBeenCalled(); }); test("handles editor sync message", async () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); const editorMessage = JSON.stringify({ type: "editor_sync", payload: { content: "
New content
" }, timestamp: Date.now(), }); await handlers["message"](editorMessage); expect(mockWs.send).toHaveBeenCalled(); }); test("handles console sync message", async () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); const consoleMessage = JSON.stringify({ type: "console_sync", payload: { id: "1", type: "log", message: "Test log", }, timestamp: Date.now(), }); await handlers["message"](consoleMessage); }); test("handles abort message", async () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); const abortMessage = JSON.stringify({ type: "abort", payload: {}, timestamp: Date.now(), }); await handlers["message"](abortMessage); expect(mockWs.send).toHaveBeenCalled(); }); test("handles clear conversation message", async () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); const clearMessage = JSON.stringify({ type: "clear_conversation", payload: {}, timestamp: Date.now(), }); await handlers["message"](clearMessage); expect(mockWs.send).toHaveBeenCalled(); }); test("handles malformed message", async () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); await handlers["message"]("invalid json"); expect(mockWs.send).toHaveBeenCalled(); const sentData = (mockWs.send as ReturnType).mock .calls[1][0] as string; const message = JSON.parse(sentData); expect(message.type).toBe("error"); }); test("cleans up on close", () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); handlers["close"](); }); test("handles connection error", () => { const handlers: Record void> = {}; mockWs.on = mock((event: string, handler: (...args: unknown[]) => void) => { handlers[event] = handler; }); manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); const error = new Error("Connection failed"); handlers["error"](error); }); test("sends status updates", () => { manager.handleConnection( mockWs as WebSocket, mockRequest as IncomingMessage, ); manager["sendMessage"](mockWs as WebSocket, { type: "status", payload: { processing: true }, timestamp: Date.now(), }); expect(mockWs.send).toHaveBeenCalled(); }); });