@dynamicu/chromedebug-mcp 2.2.0
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.
- package/CLAUDE.md +344 -0
- package/LICENSE +21 -0
- package/README.md +250 -0
- package/chrome-extension/README.md +41 -0
- package/chrome-extension/background.js +3917 -0
- package/chrome-extension/chrome-session-manager.js +706 -0
- package/chrome-extension/content.css +181 -0
- package/chrome-extension/content.js +3022 -0
- package/chrome-extension/data-buffer.js +435 -0
- package/chrome-extension/dom-tracker.js +411 -0
- package/chrome-extension/extension-config.js +78 -0
- package/chrome-extension/firebase-client.js +278 -0
- package/chrome-extension/firebase-config.js +32 -0
- package/chrome-extension/firebase-config.module.js +22 -0
- package/chrome-extension/firebase-config.module.template.js +27 -0
- package/chrome-extension/firebase-config.template.js +36 -0
- package/chrome-extension/frame-capture.js +407 -0
- package/chrome-extension/icon128.png +1 -0
- package/chrome-extension/icon16.png +1 -0
- package/chrome-extension/icon48.png +1 -0
- package/chrome-extension/license-helper.js +181 -0
- package/chrome-extension/logger.js +23 -0
- package/chrome-extension/manifest.json +73 -0
- package/chrome-extension/network-tracker.js +510 -0
- package/chrome-extension/offscreen.html +10 -0
- package/chrome-extension/options.html +203 -0
- package/chrome-extension/options.js +282 -0
- package/chrome-extension/pako.min.js +2 -0
- package/chrome-extension/performance-monitor.js +533 -0
- package/chrome-extension/pii-redactor.js +405 -0
- package/chrome-extension/popup.html +532 -0
- package/chrome-extension/popup.js +2446 -0
- package/chrome-extension/upload-manager.js +323 -0
- package/chrome-extension/web-vitals.iife.js +1 -0
- package/config/api-keys.json +11 -0
- package/config/chrome-pilot-config.json +45 -0
- package/package.json +126 -0
- package/scripts/cleanup-processes.js +109 -0
- package/scripts/config-manager.js +280 -0
- package/scripts/generate-extension-config.js +53 -0
- package/scripts/setup-security.js +64 -0
- package/src/capture/architecture.js +426 -0
- package/src/capture/error-handling-tests.md +38 -0
- package/src/capture/error-handling-types.ts +360 -0
- package/src/capture/index.js +508 -0
- package/src/capture/interfaces.js +625 -0
- package/src/capture/memory-manager.js +713 -0
- package/src/capture/types.js +342 -0
- package/src/chrome-controller.js +2658 -0
- package/src/cli.js +19 -0
- package/src/config-loader.js +303 -0
- package/src/database.js +2178 -0
- package/src/firebase-license-manager.js +462 -0
- package/src/firebase-privacy-guard.js +397 -0
- package/src/http-server.js +1516 -0
- package/src/index-direct.js +157 -0
- package/src/index-modular.js +219 -0
- package/src/index-monolithic-backup.js +2230 -0
- package/src/index.js +305 -0
- package/src/legacy/chrome-controller-old.js +1406 -0
- package/src/legacy/index-express.js +625 -0
- package/src/legacy/index-old.js +977 -0
- package/src/legacy/routes.js +260 -0
- package/src/legacy/shared-storage.js +101 -0
- package/src/logger.js +10 -0
- package/src/mcp/handlers/chrome-tool-handler.js +306 -0
- package/src/mcp/handlers/element-tool-handler.js +51 -0
- package/src/mcp/handlers/frame-tool-handler.js +957 -0
- package/src/mcp/handlers/request-handler.js +104 -0
- package/src/mcp/handlers/workflow-tool-handler.js +636 -0
- package/src/mcp/server.js +68 -0
- package/src/mcp/tools/index.js +701 -0
- package/src/middleware/auth.js +371 -0
- package/src/middleware/security.js +267 -0
- package/src/port-discovery.js +258 -0
- package/src/routes/admin.js +182 -0
- package/src/services/browser-daemon.js +494 -0
- package/src/services/chrome-service.js +375 -0
- package/src/services/failover-manager.js +412 -0
- package/src/services/git-safety-service.js +675 -0
- package/src/services/heartbeat-manager.js +200 -0
- package/src/services/http-client.js +195 -0
- package/src/services/process-manager.js +318 -0
- package/src/services/process-tracker.js +574 -0
- package/src/services/profile-manager.js +449 -0
- package/src/services/project-manager.js +415 -0
- package/src/services/session-manager.js +497 -0
- package/src/services/session-registry.js +491 -0
- package/src/services/unified-session-manager.js +678 -0
- package/src/shared-storage-old.js +267 -0
- package/src/standalone-server.js +53 -0
- package/src/utils/extension-path.js +145 -0
- package/src/utils.js +187 -0
- package/src/validation/log-transformer.js +125 -0
- package/src/validation/schemas.js +391 -0
|
@@ -0,0 +1,375 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Chrome Service Wrapper - Service layer for Chrome controller integration
|
|
3
|
+
* Provides a clean interface between MCP tools and Chrome controller
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { ProcessManager } from './process-manager.js';
|
|
7
|
+
import { discoverServer } from '../port-discovery.js';
|
|
8
|
+
import { startHttpServer } from '../http-server.js';
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* Chrome Service class that wraps ChromeController with additional services
|
|
12
|
+
* Manages HTTP server integration and process lifecycle
|
|
13
|
+
*/
|
|
14
|
+
export class ChromeService {
|
|
15
|
+
constructor(chromeController) {
|
|
16
|
+
this.chromeController = chromeController;
|
|
17
|
+
this.processManager = new ProcessManager();
|
|
18
|
+
this.httpServerPort = null;
|
|
19
|
+
this.httpServer = null;
|
|
20
|
+
|
|
21
|
+
// Add Chrome controller cleanup to process manager
|
|
22
|
+
this.processManager.addShutdownHandler(async () => {
|
|
23
|
+
await this.cleanup();
|
|
24
|
+
});
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* Initializes the Chrome service with HTTP server if needed
|
|
29
|
+
* @param {Object} options - Initialization options
|
|
30
|
+
* @returns {Promise<Object>} Initialization result
|
|
31
|
+
*/
|
|
32
|
+
async initialize(options = {}) {
|
|
33
|
+
const { startHttp = true, singleServer = false, sessionManager = null } = options;
|
|
34
|
+
|
|
35
|
+
const result = {
|
|
36
|
+
chromeService: 'initialized',
|
|
37
|
+
httpServer: null,
|
|
38
|
+
processManager: this.processManager.getStatistics()
|
|
39
|
+
};
|
|
40
|
+
|
|
41
|
+
if (startHttp && !singleServer) {
|
|
42
|
+
try {
|
|
43
|
+
// Use port from session manager if available, otherwise use discovery
|
|
44
|
+
let targetPort = null;
|
|
45
|
+
|
|
46
|
+
if (sessionManager) {
|
|
47
|
+
const sessionInfo = sessionManager.getSessionInfo();
|
|
48
|
+
if (sessionInfo && sessionInfo.port) {
|
|
49
|
+
targetPort = sessionInfo.port;
|
|
50
|
+
console.error(`Using session manager allocated port: ${targetPort}`);
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
if (!targetPort) {
|
|
55
|
+
// Fallback to discovery
|
|
56
|
+
const serverInfo = await discoverServer();
|
|
57
|
+
console.error('Falling back to port discovery');
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
const { httpServer, serverPort } = await startHttpServer(this.chromeController, targetPort);
|
|
61
|
+
|
|
62
|
+
this.httpServer = httpServer;
|
|
63
|
+
this.httpServerPort = serverPort;
|
|
64
|
+
|
|
65
|
+
result.httpServer = {
|
|
66
|
+
port: serverPort,
|
|
67
|
+
status: 'running'
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
console.error(`HTTP server started on port ${serverPort}`);
|
|
71
|
+
} catch (error) {
|
|
72
|
+
console.error('Failed to start HTTP server:', error);
|
|
73
|
+
result.httpServer = {
|
|
74
|
+
error: error.message,
|
|
75
|
+
status: 'failed'
|
|
76
|
+
};
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
return result;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
/**
|
|
84
|
+
* Gets the Chrome controller instance
|
|
85
|
+
* @returns {Object} Chrome controller
|
|
86
|
+
*/
|
|
87
|
+
getController() {
|
|
88
|
+
return this.chromeController;
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
/**
|
|
92
|
+
* Gets the process manager instance
|
|
93
|
+
* @returns {ProcessManager} Process manager
|
|
94
|
+
*/
|
|
95
|
+
getProcessManager() {
|
|
96
|
+
return this.processManager;
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
/**
|
|
100
|
+
* Gets HTTP server information
|
|
101
|
+
* @returns {Object} HTTP server info
|
|
102
|
+
*/
|
|
103
|
+
getHttpServerInfo() {
|
|
104
|
+
return {
|
|
105
|
+
port: this.httpServerPort,
|
|
106
|
+
running: !!this.httpServer,
|
|
107
|
+
server: this.httpServer
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
/**
|
|
112
|
+
* Safely launches Chrome with process management
|
|
113
|
+
* @param {Object} options - Launch options
|
|
114
|
+
* @returns {Promise<Object>} Launch result
|
|
115
|
+
*/
|
|
116
|
+
async launchChrome(options = {}) {
|
|
117
|
+
try {
|
|
118
|
+
const result = await this.chromeController.launch(options);
|
|
119
|
+
|
|
120
|
+
// Register Chrome process for management if available
|
|
121
|
+
if (result.chromeProcess && result.chromeProcess.pid) {
|
|
122
|
+
this.processManager.registerProcess(result.chromeProcess.pid);
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
return result;
|
|
126
|
+
} catch (error) {
|
|
127
|
+
console.error('Error launching Chrome:', error);
|
|
128
|
+
throw error;
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
/**
|
|
133
|
+
* Connects to existing Chrome with process management
|
|
134
|
+
* @param {number} port - Chrome debugging port
|
|
135
|
+
* @returns {Promise<Object>} Connection result
|
|
136
|
+
*/
|
|
137
|
+
async connectToExistingChrome(port = 9222) {
|
|
138
|
+
try {
|
|
139
|
+
const result = await this.chromeController.connectToExisting(port);
|
|
140
|
+
|
|
141
|
+
// Note: We don't register external Chrome processes for management
|
|
142
|
+
// since we didn't create them and shouldn't kill them
|
|
143
|
+
|
|
144
|
+
return result;
|
|
145
|
+
} catch (error) {
|
|
146
|
+
console.error('Error connecting to Chrome:', error);
|
|
147
|
+
throw error;
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
/**
|
|
152
|
+
* Alias for connectToExistingChrome for MCP ChromeToolHandler compatibility
|
|
153
|
+
* @param {number} port - Chrome debugging port
|
|
154
|
+
* @returns {Promise<Object>} Connection result
|
|
155
|
+
*/
|
|
156
|
+
async connectToExisting(port = 9222) {
|
|
157
|
+
// Alias for ChromeToolHandler compatibility
|
|
158
|
+
return this.connectToExistingChrome(port);
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
/**
|
|
162
|
+
* Force reset Chrome with comprehensive cleanup
|
|
163
|
+
* @returns {Promise<Object>} Reset result
|
|
164
|
+
*/
|
|
165
|
+
async forceReset() {
|
|
166
|
+
try {
|
|
167
|
+
// First, let the chrome controller handle its cleanup
|
|
168
|
+
const chromeResult = await this.chromeController.forceReset();
|
|
169
|
+
|
|
170
|
+
// Then use process manager to clean up any remaining processes
|
|
171
|
+
const processResult = await this.processManager.cleanupChromePilotProcesses();
|
|
172
|
+
|
|
173
|
+
return {
|
|
174
|
+
chromeController: chromeResult,
|
|
175
|
+
processCleanup: processResult,
|
|
176
|
+
httpServer: this.httpServerPort ? {
|
|
177
|
+
port: this.httpServerPort,
|
|
178
|
+
running: !!this.httpServer
|
|
179
|
+
} : null
|
|
180
|
+
};
|
|
181
|
+
} catch (error) {
|
|
182
|
+
console.error('Error during force reset:', error);
|
|
183
|
+
throw error;
|
|
184
|
+
}
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
/**
|
|
188
|
+
* Gets comprehensive connection status
|
|
189
|
+
* @returns {Promise<Object>} Status information
|
|
190
|
+
*/
|
|
191
|
+
async getStatus() {
|
|
192
|
+
const chromeStatus = await this.chromeController.getConnectionStatus();
|
|
193
|
+
const processStats = this.processManager.getStatistics();
|
|
194
|
+
const httpInfo = this.getHttpServerInfo();
|
|
195
|
+
|
|
196
|
+
return {
|
|
197
|
+
chrome: chromeStatus,
|
|
198
|
+
httpServer: httpInfo,
|
|
199
|
+
processManager: processStats,
|
|
200
|
+
timestamp: new Date().toISOString()
|
|
201
|
+
};
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
/**
|
|
205
|
+
* Cleans up all managed resources
|
|
206
|
+
* @returns {Promise<void>}
|
|
207
|
+
*/
|
|
208
|
+
async cleanup() {
|
|
209
|
+
try {
|
|
210
|
+
// Stop HTTP server if running
|
|
211
|
+
if (this.httpServer) {
|
|
212
|
+
this.httpServer.close();
|
|
213
|
+
this.httpServer = null;
|
|
214
|
+
this.httpServerPort = null;
|
|
215
|
+
}
|
|
216
|
+
|
|
217
|
+
// Clean up Chrome controller
|
|
218
|
+
if (this.chromeController && typeof this.chromeController.cleanup === 'function') {
|
|
219
|
+
await this.chromeController.cleanup();
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
console.error('Chrome service cleanup completed');
|
|
223
|
+
} catch (error) {
|
|
224
|
+
console.error('Error during Chrome service cleanup:', error);
|
|
225
|
+
}
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
// MCP Tool Interface Compatibility Methods
|
|
229
|
+
// These proxy methods provide the expected interface for MCP tools
|
|
230
|
+
|
|
231
|
+
/**
|
|
232
|
+
* Launch Chrome - proxy to launchChrome for MCP compatibility
|
|
233
|
+
* @param {Object} options - Launch options
|
|
234
|
+
* @returns {Promise<Object>} Launch result
|
|
235
|
+
*/
|
|
236
|
+
async launch(options = {}) {
|
|
237
|
+
return this.launchChrome(options);
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
/**
|
|
241
|
+
* Get connection status - proxy to chromeController for MCP compatibility
|
|
242
|
+
* @returns {Promise<Object>} Connection status
|
|
243
|
+
*/
|
|
244
|
+
async getConnectionStatus() {
|
|
245
|
+
return await this.chromeController.getConnectionStatus();
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
/**
|
|
249
|
+
* Delegates method calls to the Chrome controller
|
|
250
|
+
* This allows the service to act as a proxy while adding process management
|
|
251
|
+
*/
|
|
252
|
+
|
|
253
|
+
// Navigation methods
|
|
254
|
+
async navigateTo(url) {
|
|
255
|
+
return await this.chromeController.navigateTo(url);
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
// Debug methods
|
|
259
|
+
async pause() {
|
|
260
|
+
return await this.chromeController.pause();
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
async resume() {
|
|
264
|
+
return await this.chromeController.resume();
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
async stepOver() {
|
|
268
|
+
return await this.chromeController.stepOver();
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
async evaluate(expression) {
|
|
272
|
+
return await this.chromeController.evaluate(expression);
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
async getScopes() {
|
|
276
|
+
return await this.chromeController.getScopes();
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
async setBreakpoint(url, lineNumber) {
|
|
280
|
+
return await this.chromeController.setBreakpoint(url, lineNumber);
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
// Content methods
|
|
284
|
+
async takeScreenshot(options) {
|
|
285
|
+
return await this.chromeController.takeScreenshot(options);
|
|
286
|
+
}
|
|
287
|
+
|
|
288
|
+
async getPageContent(options) {
|
|
289
|
+
return await this.chromeController.getPageContent(options);
|
|
290
|
+
}
|
|
291
|
+
|
|
292
|
+
// Element methods
|
|
293
|
+
async getSelectedElement() {
|
|
294
|
+
return await this.chromeController.getSelectedElement();
|
|
295
|
+
}
|
|
296
|
+
|
|
297
|
+
async applyToSelectedElement(css) {
|
|
298
|
+
return await this.chromeController.applyToSelectedElement(css);
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
async executeOnSelectedElement(code) {
|
|
302
|
+
return await this.chromeController.executeOnSelectedElement(code);
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
async clearSelectedElement() {
|
|
306
|
+
return await this.chromeController.clearSelectedElement();
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
// Workflow methods
|
|
310
|
+
async getWorkflowRecording(sessionId) {
|
|
311
|
+
return await this.chromeController.getWorkflowRecording(sessionId);
|
|
312
|
+
}
|
|
313
|
+
|
|
314
|
+
async listWorkflowRecordings() {
|
|
315
|
+
return await this.chromeController.listWorkflowRecordings();
|
|
316
|
+
}
|
|
317
|
+
|
|
318
|
+
async saveRestorePoint(data) {
|
|
319
|
+
return await this.chromeController.saveRestorePoint(data);
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
async getRestorePoint(id) {
|
|
323
|
+
return await this.chromeController.getRestorePoint(id);
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
async listRestorePoints(workflowId) {
|
|
327
|
+
return await this.chromeController.listRestorePoints(workflowId);
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
async playWorkflowRecording(sessionId, speed) {
|
|
331
|
+
return await this.chromeController.playWorkflowRecording(sessionId, speed);
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
async playWorkflowByName(name, speed) {
|
|
335
|
+
return await this.chromeController.playWorkflowByName(name, speed);
|
|
336
|
+
}
|
|
337
|
+
|
|
338
|
+
// Frame methods
|
|
339
|
+
async getFrameSessionInfo(sessionId) {
|
|
340
|
+
return await this.chromeController.getFrameSessionInfo(sessionId);
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
async listFrameSessions() {
|
|
344
|
+
return await this.chromeController.listFrameSessions();
|
|
345
|
+
}
|
|
346
|
+
|
|
347
|
+
async getFrame(sessionId, frameIndex) {
|
|
348
|
+
return await this.chromeController.getFrame(sessionId, frameIndex);
|
|
349
|
+
}
|
|
350
|
+
|
|
351
|
+
async searchFrameLogs(sessionId, searchText, logLevel, maxResults) {
|
|
352
|
+
return await this.chromeController.searchFrameLogs(sessionId, searchText, logLevel, maxResults);
|
|
353
|
+
}
|
|
354
|
+
|
|
355
|
+
async getFrameLogsPaginated(sessionId, frameIndex, offset, limit, logLevel, searchText) {
|
|
356
|
+
return await this.chromeController.getFrameLogsPaginated(sessionId, frameIndex, offset, limit, logLevel, searchText);
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
async getScreenInteractions(sessionId) {
|
|
360
|
+
return await this.chromeController.getScreenInteractions(sessionId);
|
|
361
|
+
}
|
|
362
|
+
|
|
363
|
+
async getFrameInteractions(sessionId, frameIndex) {
|
|
364
|
+
return await this.chromeController.getFrameInteractions(sessionId, frameIndex);
|
|
365
|
+
}
|
|
366
|
+
|
|
367
|
+
// Utility methods
|
|
368
|
+
getLogs() {
|
|
369
|
+
return this.chromeController.getLogs();
|
|
370
|
+
}
|
|
371
|
+
|
|
372
|
+
async getPage() {
|
|
373
|
+
return await this.chromeController.getPage();
|
|
374
|
+
}
|
|
375
|
+
}
|