@sparkleideas/mcp 3.0.0-alpha.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (279) hide show
  1. package/.claude/agents/analysis/analyze-code-quality.md +179 -0
  2. package/.claude/agents/analysis/code-analyzer.md +210 -0
  3. package/.claude/agents/analysis/code-review/analyze-code-quality.md +179 -0
  4. package/.claude/agents/architecture/arch-system-design.md +157 -0
  5. package/.claude/agents/architecture/system-design/arch-system-design.md +155 -0
  6. package/.claude/agents/consensus/byzantine-coordinator.md +63 -0
  7. package/.claude/agents/consensus/crdt-synchronizer.md +997 -0
  8. package/.claude/agents/consensus/gossip-coordinator.md +63 -0
  9. package/.claude/agents/consensus/performance-benchmarker.md +851 -0
  10. package/.claude/agents/consensus/quorum-manager.md +823 -0
  11. package/.claude/agents/consensus/raft-manager.md +63 -0
  12. package/.claude/agents/consensus/security-manager.md +622 -0
  13. package/.claude/agents/core/coder.md +453 -0
  14. package/.claude/agents/core/planner.md +375 -0
  15. package/.claude/agents/core/researcher.md +369 -0
  16. package/.claude/agents/core/reviewer.md +520 -0
  17. package/.claude/agents/core/tester.md +512 -0
  18. package/.claude/agents/custom/test-long-runner.md +44 -0
  19. package/.claude/agents/data/data-ml-model.md +445 -0
  20. package/.claude/agents/data/ml/data-ml-model.md +193 -0
  21. package/.claude/agents/development/backend/dev-backend-api.md +142 -0
  22. package/.claude/agents/development/dev-backend-api.md +345 -0
  23. package/.claude/agents/devops/ci-cd/ops-cicd-github.md +164 -0
  24. package/.claude/agents/devops/ops-cicd-github.md +165 -0
  25. package/.claude/agents/documentation/api-docs/docs-api-openapi.md +174 -0
  26. package/.claude/agents/documentation/docs-api-openapi.md +355 -0
  27. package/.claude/agents/flow-nexus/app-store.md +88 -0
  28. package/.claude/agents/flow-nexus/authentication.md +69 -0
  29. package/.claude/agents/flow-nexus/challenges.md +81 -0
  30. package/.claude/agents/flow-nexus/neural-network.md +88 -0
  31. package/.claude/agents/flow-nexus/payments.md +83 -0
  32. package/.claude/agents/flow-nexus/sandbox.md +76 -0
  33. package/.claude/agents/flow-nexus/swarm.md +76 -0
  34. package/.claude/agents/flow-nexus/user-tools.md +96 -0
  35. package/.claude/agents/flow-nexus/workflow.md +84 -0
  36. package/.claude/agents/github/code-review-swarm.md +377 -0
  37. package/.claude/agents/github/github-modes.md +173 -0
  38. package/.claude/agents/github/issue-tracker.md +576 -0
  39. package/.claude/agents/github/multi-repo-swarm.md +553 -0
  40. package/.claude/agents/github/pr-manager.md +438 -0
  41. package/.claude/agents/github/project-board-sync.md +509 -0
  42. package/.claude/agents/github/release-manager.md +605 -0
  43. package/.claude/agents/github/release-swarm.md +583 -0
  44. package/.claude/agents/github/repo-architect.md +398 -0
  45. package/.claude/agents/github/swarm-issue.md +573 -0
  46. package/.claude/agents/github/swarm-pr.md +428 -0
  47. package/.claude/agents/github/sync-coordinator.md +452 -0
  48. package/.claude/agents/github/workflow-automation.md +903 -0
  49. package/.claude/agents/goal/agent.md +816 -0
  50. package/.claude/agents/goal/goal-planner.md +73 -0
  51. package/.claude/agents/optimization/benchmark-suite.md +665 -0
  52. package/.claude/agents/optimization/load-balancer.md +431 -0
  53. package/.claude/agents/optimization/performance-monitor.md +672 -0
  54. package/.claude/agents/optimization/resource-allocator.md +674 -0
  55. package/.claude/agents/optimization/topology-optimizer.md +808 -0
  56. package/.claude/agents/payments/agentic-payments.md +126 -0
  57. package/.claude/agents/sona/sona-learning-optimizer.md +74 -0
  58. package/.claude/agents/sparc/architecture.md +699 -0
  59. package/.claude/agents/sparc/pseudocode.md +520 -0
  60. package/.claude/agents/sparc/refinement.md +802 -0
  61. package/.claude/agents/sparc/specification.md +478 -0
  62. package/.claude/agents/specialized/mobile/spec-mobile-react-native.md +225 -0
  63. package/.claude/agents/specialized/spec-mobile-react-native.md +227 -0
  64. package/.claude/agents/sublinear/consensus-coordinator.md +338 -0
  65. package/.claude/agents/sublinear/matrix-optimizer.md +185 -0
  66. package/.claude/agents/sublinear/pagerank-analyzer.md +299 -0
  67. package/.claude/agents/sublinear/performance-optimizer.md +368 -0
  68. package/.claude/agents/sublinear/trading-predictor.md +246 -0
  69. package/.claude/agents/swarm/adaptive-coordinator.md +1127 -0
  70. package/.claude/agents/swarm/hierarchical-coordinator.md +710 -0
  71. package/.claude/agents/swarm/mesh-coordinator.md +963 -0
  72. package/.claude/agents/templates/automation-smart-agent.md +205 -0
  73. package/.claude/agents/templates/base-template-generator.md +268 -0
  74. package/.claude/agents/templates/coordinator-swarm-init.md +90 -0
  75. package/.claude/agents/templates/github-pr-manager.md +177 -0
  76. package/.claude/agents/templates/implementer-sparc-coder.md +259 -0
  77. package/.claude/agents/templates/memory-coordinator.md +187 -0
  78. package/.claude/agents/templates/orchestrator-task.md +139 -0
  79. package/.claude/agents/templates/performance-analyzer.md +199 -0
  80. package/.claude/agents/templates/sparc-coordinator.md +514 -0
  81. package/.claude/agents/testing/production-validator.md +395 -0
  82. package/.claude/agents/testing/tdd-london-swarm.md +244 -0
  83. package/.claude/agents/v3/adr-architect.md +184 -0
  84. package/.claude/agents/v3/aidefence-guardian.md +282 -0
  85. package/.claude/agents/v3/claims-authorizer.md +208 -0
  86. package/.claude/agents/v3/collective-intelligence-coordinator.md +993 -0
  87. package/.claude/agents/v3/ddd-domain-expert.md +220 -0
  88. package/.claude/agents/v3/injection-analyst.md +236 -0
  89. package/.claude/agents/v3/memory-specialist.md +995 -0
  90. package/.claude/agents/v3/performance-engineer.md +1233 -0
  91. package/.claude/agents/v3/pii-detector.md +151 -0
  92. package/.claude/agents/v3/reasoningbank-learner.md +213 -0
  93. package/.claude/agents/v3/security-architect-aidefence.md +410 -0
  94. package/.claude/agents/v3/security-architect.md +867 -0
  95. package/.claude/agents/v3/security-auditor.md +771 -0
  96. package/.claude/agents/v3/sparc-orchestrator.md +182 -0
  97. package/.claude/agents/v3/swarm-memory-manager.md +157 -0
  98. package/.claude/agents/v3/v3-integration-architect.md +205 -0
  99. package/.claude/commands/analysis/COMMAND_COMPLIANCE_REPORT.md +54 -0
  100. package/.claude/commands/analysis/README.md +9 -0
  101. package/.claude/commands/analysis/bottleneck-detect.md +162 -0
  102. package/.claude/commands/analysis/performance-bottlenecks.md +59 -0
  103. package/.claude/commands/analysis/performance-report.md +25 -0
  104. package/.claude/commands/analysis/token-efficiency.md +45 -0
  105. package/.claude/commands/analysis/token-usage.md +25 -0
  106. package/.claude/commands/automation/README.md +9 -0
  107. package/.claude/commands/automation/auto-agent.md +122 -0
  108. package/.claude/commands/automation/self-healing.md +106 -0
  109. package/.claude/commands/automation/session-memory.md +90 -0
  110. package/.claude/commands/automation/smart-agents.md +73 -0
  111. package/.claude/commands/automation/smart-spawn.md +25 -0
  112. package/.claude/commands/automation/workflow-select.md +25 -0
  113. package/.claude/commands/claude-flow-help.md +103 -0
  114. package/.claude/commands/claude-flow-memory.md +107 -0
  115. package/.claude/commands/claude-flow-swarm.md +205 -0
  116. package/.claude/commands/github/README.md +11 -0
  117. package/.claude/commands/github/code-review-swarm.md +514 -0
  118. package/.claude/commands/github/code-review.md +25 -0
  119. package/.claude/commands/github/github-modes.md +147 -0
  120. package/.claude/commands/github/github-swarm.md +121 -0
  121. package/.claude/commands/github/issue-tracker.md +292 -0
  122. package/.claude/commands/github/issue-triage.md +25 -0
  123. package/.claude/commands/github/multi-repo-swarm.md +519 -0
  124. package/.claude/commands/github/pr-enhance.md +26 -0
  125. package/.claude/commands/github/pr-manager.md +170 -0
  126. package/.claude/commands/github/project-board-sync.md +471 -0
  127. package/.claude/commands/github/release-manager.md +338 -0
  128. package/.claude/commands/github/release-swarm.md +544 -0
  129. package/.claude/commands/github/repo-analyze.md +25 -0
  130. package/.claude/commands/github/repo-architect.md +367 -0
  131. package/.claude/commands/github/swarm-issue.md +482 -0
  132. package/.claude/commands/github/swarm-pr.md +285 -0
  133. package/.claude/commands/github/sync-coordinator.md +301 -0
  134. package/.claude/commands/github/workflow-automation.md +442 -0
  135. package/.claude/commands/hooks/README.md +11 -0
  136. package/.claude/commands/hooks/overview.md +58 -0
  137. package/.claude/commands/hooks/post-edit.md +117 -0
  138. package/.claude/commands/hooks/post-task.md +112 -0
  139. package/.claude/commands/hooks/pre-edit.md +113 -0
  140. package/.claude/commands/hooks/pre-task.md +111 -0
  141. package/.claude/commands/hooks/session-end.md +118 -0
  142. package/.claude/commands/hooks/setup.md +103 -0
  143. package/.claude/commands/monitoring/README.md +9 -0
  144. package/.claude/commands/monitoring/agent-metrics.md +25 -0
  145. package/.claude/commands/monitoring/agents.md +44 -0
  146. package/.claude/commands/monitoring/real-time-view.md +25 -0
  147. package/.claude/commands/monitoring/status.md +46 -0
  148. package/.claude/commands/monitoring/swarm-monitor.md +25 -0
  149. package/.claude/commands/optimization/README.md +9 -0
  150. package/.claude/commands/optimization/auto-topology.md +62 -0
  151. package/.claude/commands/optimization/cache-manage.md +25 -0
  152. package/.claude/commands/optimization/parallel-execute.md +25 -0
  153. package/.claude/commands/optimization/parallel-execution.md +50 -0
  154. package/.claude/commands/optimization/topology-optimize.md +25 -0
  155. package/.claude/commands/sparc/analyzer.md +52 -0
  156. package/.claude/commands/sparc/architect.md +53 -0
  157. package/.claude/commands/sparc/ask.md +97 -0
  158. package/.claude/commands/sparc/batch-executor.md +54 -0
  159. package/.claude/commands/sparc/code.md +89 -0
  160. package/.claude/commands/sparc/coder.md +54 -0
  161. package/.claude/commands/sparc/debug.md +83 -0
  162. package/.claude/commands/sparc/debugger.md +54 -0
  163. package/.claude/commands/sparc/designer.md +53 -0
  164. package/.claude/commands/sparc/devops.md +109 -0
  165. package/.claude/commands/sparc/docs-writer.md +80 -0
  166. package/.claude/commands/sparc/documenter.md +54 -0
  167. package/.claude/commands/sparc/innovator.md +54 -0
  168. package/.claude/commands/sparc/integration.md +83 -0
  169. package/.claude/commands/sparc/mcp.md +117 -0
  170. package/.claude/commands/sparc/memory-manager.md +54 -0
  171. package/.claude/commands/sparc/optimizer.md +54 -0
  172. package/.claude/commands/sparc/orchestrator.md +132 -0
  173. package/.claude/commands/sparc/post-deployment-monitoring-mode.md +83 -0
  174. package/.claude/commands/sparc/refinement-optimization-mode.md +83 -0
  175. package/.claude/commands/sparc/researcher.md +54 -0
  176. package/.claude/commands/sparc/reviewer.md +54 -0
  177. package/.claude/commands/sparc/security-review.md +80 -0
  178. package/.claude/commands/sparc/sparc-modes.md +174 -0
  179. package/.claude/commands/sparc/sparc.md +111 -0
  180. package/.claude/commands/sparc/spec-pseudocode.md +80 -0
  181. package/.claude/commands/sparc/supabase-admin.md +348 -0
  182. package/.claude/commands/sparc/swarm-coordinator.md +54 -0
  183. package/.claude/commands/sparc/tdd.md +54 -0
  184. package/.claude/commands/sparc/tester.md +54 -0
  185. package/.claude/commands/sparc/tutorial.md +79 -0
  186. package/.claude/commands/sparc/workflow-manager.md +54 -0
  187. package/.claude/helpers/README.md +97 -0
  188. package/.claude/helpers/adr-compliance.sh +186 -0
  189. package/.claude/helpers/auto-commit.sh +178 -0
  190. package/.claude/helpers/checkpoint-manager.sh +251 -0
  191. package/.claude/helpers/daemon-manager.sh +252 -0
  192. package/.claude/helpers/ddd-tracker.sh +144 -0
  193. package/.claude/helpers/github-safe.js +106 -0
  194. package/.claude/helpers/github-setup.sh +28 -0
  195. package/.claude/helpers/guidance-hook.sh +13 -0
  196. package/.claude/helpers/guidance-hooks.sh +102 -0
  197. package/.claude/helpers/health-monitor.sh +108 -0
  198. package/.claude/helpers/learning-hooks.sh +329 -0
  199. package/.claude/helpers/learning-optimizer.sh +127 -0
  200. package/.claude/helpers/learning-service.mjs +1144 -0
  201. package/.claude/helpers/memory.js +83 -0
  202. package/.claude/helpers/metrics-db.mjs +488 -0
  203. package/.claude/helpers/pattern-consolidator.sh +86 -0
  204. package/.claude/helpers/perf-worker.sh +160 -0
  205. package/.claude/helpers/post-commit +16 -0
  206. package/.claude/helpers/pre-commit +26 -0
  207. package/.claude/helpers/quick-start.sh +19 -0
  208. package/.claude/helpers/router.js +66 -0
  209. package/.claude/helpers/security-scanner.sh +127 -0
  210. package/.claude/helpers/session.js +127 -0
  211. package/.claude/helpers/setup-mcp.sh +18 -0
  212. package/.claude/helpers/standard-checkpoint-hooks.sh +189 -0
  213. package/.claude/helpers/statusline-hook.sh +21 -0
  214. package/.claude/helpers/statusline.cjs +509 -0
  215. package/.claude/helpers/statusline.js +316 -0
  216. package/.claude/helpers/swarm-comms.sh +353 -0
  217. package/.claude/helpers/swarm-hooks.sh +761 -0
  218. package/.claude/helpers/swarm-monitor.sh +211 -0
  219. package/.claude/helpers/sync-v3-metrics.sh +245 -0
  220. package/.claude/helpers/update-v3-progress.sh +166 -0
  221. package/.claude/helpers/v3-quick-status.sh +58 -0
  222. package/.claude/helpers/v3.sh +111 -0
  223. package/.claude/helpers/validate-v3-config.sh +216 -0
  224. package/.claude/helpers/worker-manager.sh +170 -0
  225. package/.claude/settings.json +237 -0
  226. package/.claude/skills/agentdb-advanced/SKILL.md +550 -0
  227. package/.claude/skills/agentdb-learning/SKILL.md +545 -0
  228. package/.claude/skills/agentdb-memory-patterns/SKILL.md +339 -0
  229. package/.claude/skills/agentdb-optimization/SKILL.md +509 -0
  230. package/.claude/skills/agentdb-vector-search/SKILL.md +339 -0
  231. package/.claude/skills/github-code-review/SKILL.md +1140 -0
  232. package/.claude/skills/github-multi-repo/SKILL.md +874 -0
  233. package/.claude/skills/github-project-management/SKILL.md +1277 -0
  234. package/.claude/skills/github-release-management/SKILL.md +1081 -0
  235. package/.claude/skills/github-workflow-automation/SKILL.md +1065 -0
  236. package/.claude/skills/hooks-automation/SKILL.md +1201 -0
  237. package/.claude/skills/pair-programming/SKILL.md +1202 -0
  238. package/.claude/skills/reasoningbank-agentdb/SKILL.md +446 -0
  239. package/.claude/skills/reasoningbank-intelligence/SKILL.md +201 -0
  240. package/.claude/skills/skill-builder/SKILL.md +910 -0
  241. package/.claude/skills/sparc-methodology/SKILL.md +1115 -0
  242. package/.claude/skills/stream-chain/SKILL.md +563 -0
  243. package/.claude/skills/swarm-advanced/SKILL.md +973 -0
  244. package/.claude/skills/swarm-orchestration/SKILL.md +179 -0
  245. package/.claude/skills/v3-cli-modernization/SKILL.md +872 -0
  246. package/.claude/skills/v3-core-implementation/SKILL.md +797 -0
  247. package/.claude/skills/v3-ddd-architecture/SKILL.md +442 -0
  248. package/.claude/skills/v3-integration-deep/SKILL.md +241 -0
  249. package/.claude/skills/v3-mcp-optimization/SKILL.md +777 -0
  250. package/.claude/skills/v3-memory-unification/SKILL.md +174 -0
  251. package/.claude/skills/v3-performance-optimization/SKILL.md +390 -0
  252. package/.claude/skills/v3-security-overhaul/SKILL.md +82 -0
  253. package/.claude/skills/v3-swarm-coordination/SKILL.md +340 -0
  254. package/.claude/skills/verification-quality/SKILL.md +649 -0
  255. package/CLAUDE.md +711 -0
  256. package/README.md +428 -0
  257. package/__tests__/integration.test.ts +449 -0
  258. package/__tests__/mcp.test.ts +641 -0
  259. package/package.json +44 -0
  260. package/src/connection-pool.ts +344 -0
  261. package/src/index.ts +253 -0
  262. package/src/oauth.ts +447 -0
  263. package/src/prompt-registry.ts +296 -0
  264. package/src/rate-limiter.ts +266 -0
  265. package/src/resource-registry.ts +530 -0
  266. package/src/sampling.ts +363 -0
  267. package/src/schema-validator.ts +213 -0
  268. package/src/server.ts +1134 -0
  269. package/src/session-manager.ts +339 -0
  270. package/src/task-manager.ts +427 -0
  271. package/src/tool-registry.ts +475 -0
  272. package/src/transport/http.ts +532 -0
  273. package/src/transport/index.ts +233 -0
  274. package/src/transport/stdio.ts +252 -0
  275. package/src/transport/websocket.ts +396 -0
  276. package/src/types.ts +664 -0
  277. package/tmp.json +0 -0
  278. package/tsconfig.json +20 -0
  279. package/vitest.config.ts +13 -0
@@ -0,0 +1,396 @@
1
+ /**
2
+ * @sparkleideas/mcp - WebSocket Transport
3
+ *
4
+ * Standalone WebSocket transport with heartbeat
5
+ */
6
+
7
+ import { EventEmitter } from 'events';
8
+ import { WebSocketServer, WebSocket, RawData } from 'ws';
9
+ import { createServer, Server } from 'http';
10
+ import type {
11
+ ITransport,
12
+ TransportType,
13
+ MCPRequest,
14
+ MCPResponse,
15
+ MCPNotification,
16
+ RequestHandler,
17
+ NotificationHandler,
18
+ TransportHealthStatus,
19
+ ILogger,
20
+ AuthConfig,
21
+ } from '../types.js';
22
+
23
+ export interface WebSocketTransportConfig {
24
+ host: string;
25
+ port: number;
26
+ path?: string;
27
+ maxConnections?: number;
28
+ heartbeatInterval?: number;
29
+ heartbeatTimeout?: number;
30
+ maxMessageSize?: number;
31
+ auth?: AuthConfig;
32
+ enableBinaryMode?: boolean;
33
+ }
34
+
35
+ interface ClientConnection {
36
+ id: string;
37
+ ws: WebSocket;
38
+ createdAt: Date;
39
+ lastActivity: Date;
40
+ messageCount: number;
41
+ isAlive: boolean;
42
+ isAuthenticated: boolean;
43
+ }
44
+
45
+ export class WebSocketTransport extends EventEmitter implements ITransport {
46
+ public readonly type: TransportType = 'websocket';
47
+
48
+ private requestHandler?: RequestHandler;
49
+ private notificationHandler?: NotificationHandler;
50
+ private server?: Server;
51
+ private wss?: WebSocketServer;
52
+ private clients: Map<string, ClientConnection> = new Map();
53
+ private heartbeatTimer?: NodeJS.Timeout;
54
+ private running = false;
55
+ private connectionCounter = 0;
56
+
57
+ private messagesReceived = 0;
58
+ private messagesSent = 0;
59
+ private errors = 0;
60
+ private totalConnections = 0;
61
+
62
+ constructor(
63
+ private readonly logger: ILogger,
64
+ private readonly config: WebSocketTransportConfig
65
+ ) {
66
+ super();
67
+ }
68
+
69
+ async start(): Promise<void> {
70
+ if (this.running) {
71
+ throw new Error('WebSocket transport already running');
72
+ }
73
+
74
+ this.logger.info('Starting WebSocket transport', {
75
+ host: this.config.host,
76
+ port: this.config.port,
77
+ path: this.config.path || '/ws',
78
+ });
79
+
80
+ this.server = createServer((req, res) => {
81
+ res.writeHead(426, { 'Content-Type': 'text/plain' });
82
+ res.end('Upgrade Required - WebSocket connection expected');
83
+ });
84
+
85
+ this.wss = new WebSocketServer({
86
+ server: this.server,
87
+ path: this.config.path || '/ws',
88
+ maxPayload: this.config.maxMessageSize || 10 * 1024 * 1024,
89
+ perMessageDeflate: true,
90
+ });
91
+
92
+ this.setupWebSocketHandlers();
93
+ this.startHeartbeat();
94
+
95
+ await new Promise<void>((resolve, reject) => {
96
+ this.server!.listen(this.config.port, this.config.host, () => {
97
+ resolve();
98
+ });
99
+ this.server!.on('error', reject);
100
+ });
101
+
102
+ this.running = true;
103
+ this.logger.info('WebSocket transport started', {
104
+ url: `ws://${this.config.host}:${this.config.port}${this.config.path || '/ws'}`,
105
+ });
106
+ }
107
+
108
+ async stop(): Promise<void> {
109
+ if (!this.running) {
110
+ return;
111
+ }
112
+
113
+ this.logger.info('Stopping WebSocket transport');
114
+ this.running = false;
115
+
116
+ this.stopHeartbeat();
117
+
118
+ for (const client of this.clients.values()) {
119
+ try {
120
+ client.ws.close(1000, 'Server shutting down');
121
+ } catch {
122
+ // Ignore errors
123
+ }
124
+ }
125
+ this.clients.clear();
126
+
127
+ if (this.wss) {
128
+ this.wss.close();
129
+ this.wss = undefined;
130
+ }
131
+
132
+ if (this.server) {
133
+ await new Promise<void>((resolve) => {
134
+ this.server!.close(() => resolve());
135
+ });
136
+ this.server = undefined;
137
+ }
138
+
139
+ this.logger.info('WebSocket transport stopped');
140
+ }
141
+
142
+ onRequest(handler: RequestHandler): void {
143
+ this.requestHandler = handler;
144
+ }
145
+
146
+ onNotification(handler: NotificationHandler): void {
147
+ this.notificationHandler = handler;
148
+ }
149
+
150
+ async getHealthStatus(): Promise<TransportHealthStatus> {
151
+ return {
152
+ healthy: this.running,
153
+ metrics: {
154
+ messagesReceived: this.messagesReceived,
155
+ messagesSent: this.messagesSent,
156
+ errors: this.errors,
157
+ activeConnections: this.clients.size,
158
+ totalConnections: this.totalConnections,
159
+ },
160
+ };
161
+ }
162
+
163
+ async sendNotification(notification: MCPNotification): Promise<void> {
164
+ const message = this.serializeMessage(notification);
165
+
166
+ for (const client of this.clients.values()) {
167
+ try {
168
+ if (client.ws.readyState === WebSocket.OPEN) {
169
+ client.ws.send(message);
170
+ this.messagesSent++;
171
+ }
172
+ } catch (error) {
173
+ this.logger.error('Failed to send notification', { clientId: client.id, error });
174
+ this.errors++;
175
+ }
176
+ }
177
+ }
178
+
179
+ async sendToClient(clientId: string, notification: MCPNotification): Promise<boolean> {
180
+ const client = this.clients.get(clientId);
181
+ if (!client || client.ws.readyState !== WebSocket.OPEN) {
182
+ return false;
183
+ }
184
+
185
+ try {
186
+ client.ws.send(this.serializeMessage(notification));
187
+ this.messagesSent++;
188
+ return true;
189
+ } catch (error) {
190
+ this.logger.error('Failed to send to client', { clientId, error });
191
+ this.errors++;
192
+ return false;
193
+ }
194
+ }
195
+
196
+ getClients(): string[] {
197
+ return Array.from(this.clients.keys());
198
+ }
199
+
200
+ getClientInfo(clientId: string): ClientConnection | undefined {
201
+ return this.clients.get(clientId);
202
+ }
203
+
204
+ disconnectClient(clientId: string, reason = 'Disconnected by server'): boolean {
205
+ const client = this.clients.get(clientId);
206
+ if (!client) {
207
+ return false;
208
+ }
209
+
210
+ try {
211
+ client.ws.close(1000, reason);
212
+ return true;
213
+ } catch {
214
+ return false;
215
+ }
216
+ }
217
+
218
+ private setupWebSocketHandlers(): void {
219
+ if (!this.wss) return;
220
+
221
+ this.wss.on('connection', (ws) => {
222
+ if (this.config.maxConnections && this.clients.size >= this.config.maxConnections) {
223
+ this.logger.warn('Max connections reached, rejecting client');
224
+ ws.close(1013, 'Server at capacity');
225
+ return;
226
+ }
227
+
228
+ const clientId = `client-${++this.connectionCounter}`;
229
+ const client: ClientConnection = {
230
+ id: clientId,
231
+ ws,
232
+ createdAt: new Date(),
233
+ lastActivity: new Date(),
234
+ messageCount: 0,
235
+ isAlive: true,
236
+ isAuthenticated: !this.config.auth?.enabled,
237
+ };
238
+
239
+ this.clients.set(clientId, client);
240
+ this.totalConnections++;
241
+
242
+ this.logger.info('Client connected', {
243
+ id: clientId,
244
+ total: this.clients.size,
245
+ });
246
+
247
+ ws.on('message', async (data) => {
248
+ await this.handleMessage(client, data);
249
+ });
250
+
251
+ ws.on('pong', () => {
252
+ client.isAlive = true;
253
+ });
254
+
255
+ ws.on('close', (code, reason) => {
256
+ this.clients.delete(clientId);
257
+ this.logger.info('Client disconnected', {
258
+ id: clientId,
259
+ code,
260
+ reason: reason.toString(),
261
+ total: this.clients.size,
262
+ });
263
+ this.emit('client:disconnected', clientId);
264
+ });
265
+
266
+ ws.on('error', (error) => {
267
+ this.logger.error('Client error', { id: clientId, error });
268
+ this.errors++;
269
+ this.clients.delete(clientId);
270
+ });
271
+
272
+ this.emit('client:connected', clientId);
273
+ });
274
+ }
275
+
276
+ private async handleMessage(client: ClientConnection, data: RawData): Promise<void> {
277
+ client.lastActivity = new Date();
278
+ client.messageCount++;
279
+ this.messagesReceived++;
280
+
281
+ try {
282
+ const message = this.parseMessage(data);
283
+
284
+ if (!client.isAuthenticated && this.config.auth?.enabled) {
285
+ if (message.method !== 'authenticate') {
286
+ client.ws.send(this.serializeMessage({
287
+ jsonrpc: '2.0',
288
+ id: message.id || null,
289
+ error: { code: -32001, message: 'Authentication required' },
290
+ } as MCPResponse));
291
+ return;
292
+ }
293
+ }
294
+
295
+ if (message.jsonrpc !== '2.0') {
296
+ client.ws.send(this.serializeMessage({
297
+ jsonrpc: '2.0',
298
+ id: message.id || null,
299
+ error: { code: -32600, message: 'Invalid JSON-RPC version' },
300
+ } as MCPResponse));
301
+ return;
302
+ }
303
+
304
+ if (message.id === undefined) {
305
+ if (this.notificationHandler) {
306
+ await this.notificationHandler(message as MCPNotification);
307
+ }
308
+ } else {
309
+ if (!this.requestHandler) {
310
+ client.ws.send(this.serializeMessage({
311
+ jsonrpc: '2.0',
312
+ id: message.id,
313
+ error: { code: -32603, message: 'No request handler' },
314
+ } as MCPResponse));
315
+ return;
316
+ }
317
+
318
+ const startTime = performance.now();
319
+ const response = await this.requestHandler(message as MCPRequest);
320
+ const duration = performance.now() - startTime;
321
+
322
+ this.logger.debug('Request processed', {
323
+ clientId: client.id,
324
+ method: message.method,
325
+ duration: `${duration.toFixed(2)}ms`,
326
+ });
327
+
328
+ client.ws.send(this.serializeMessage(response));
329
+ this.messagesSent++;
330
+ }
331
+ } catch (error) {
332
+ this.errors++;
333
+ this.logger.error('Message handling error', { clientId: client.id, error });
334
+
335
+ try {
336
+ client.ws.send(this.serializeMessage({
337
+ jsonrpc: '2.0',
338
+ id: null,
339
+ error: { code: -32700, message: 'Parse error' },
340
+ } as MCPResponse));
341
+ } catch {
342
+ // Ignore send errors
343
+ }
344
+ }
345
+ }
346
+
347
+ private parseMessage(data: RawData): any {
348
+ if (this.config.enableBinaryMode && Buffer.isBuffer(data)) {
349
+ return JSON.parse(data.toString());
350
+ }
351
+ return JSON.parse(data.toString());
352
+ }
353
+
354
+ private serializeMessage(message: MCPResponse | MCPNotification): string | Buffer {
355
+ if (this.config.enableBinaryMode) {
356
+ return JSON.stringify(message);
357
+ }
358
+ return JSON.stringify(message);
359
+ }
360
+
361
+ private startHeartbeat(): void {
362
+ const interval = this.config.heartbeatInterval || 30000;
363
+
364
+ this.heartbeatTimer = setInterval(() => {
365
+ for (const client of this.clients.values()) {
366
+ if (!client.isAlive) {
367
+ this.logger.warn('Client heartbeat timeout', { id: client.id });
368
+ client.ws.terminate();
369
+ this.clients.delete(client.id);
370
+ continue;
371
+ }
372
+
373
+ client.isAlive = false;
374
+ try {
375
+ client.ws.ping();
376
+ } catch {
377
+ // Ignore ping errors
378
+ }
379
+ }
380
+ }, interval);
381
+ }
382
+
383
+ private stopHeartbeat(): void {
384
+ if (this.heartbeatTimer) {
385
+ clearInterval(this.heartbeatTimer);
386
+ this.heartbeatTimer = undefined;
387
+ }
388
+ }
389
+ }
390
+
391
+ export function createWebSocketTransport(
392
+ logger: ILogger,
393
+ config: WebSocketTransportConfig
394
+ ): WebSocketTransport {
395
+ return new WebSocketTransport(logger, config);
396
+ }