@arvoretech/runtime-lens-mcp 1.0.0 → 1.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/README.md +10 -3
- package/agent/index.ts +281 -212
- package/dist/agent/index.js +282 -0
- package/dist/agent/index.js.map +7 -0
- package/dist/agent-bridge.d.ts +20 -0
- package/dist/agent-bridge.d.ts.map +1 -0
- package/dist/agent-bridge.js +185 -0
- package/dist/agent-bridge.js.map +1 -0
- package/dist/extension/extension.js +433 -0
- package/dist/extension/extension.js.map +7 -0
- package/dist/server.d.ts +1 -0
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +115 -100
- package/dist/server.js.map +1 -1
- package/package.json +2 -2
- package/src/agent-bridge.ts +218 -0
- package/src/server.ts +405 -358
- package/.vscodeignore +0 -21
- package/agent/tsconfig.json +0 -17
- package/eslint.config.js +0 -41
- package/extension/decorator.ts +0 -144
- package/extension/extension.ts +0 -98
- package/extension/runtime-bridge.ts +0 -206
- package/extension/tsconfig.json +0 -17
- package/tsconfig.json +0 -20
- package/vitest.config.ts +0 -13
package/src/server.ts
CHANGED
|
@@ -1,387 +1,434 @@
|
|
|
1
1
|
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
|
|
2
2
|
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
|
|
3
|
+
import { AgentBridge } from "./agent-bridge.js";
|
|
3
4
|
import { LogCollector } from "./log-collector.js";
|
|
4
5
|
import { ProcessInspector } from "./process-inspector.js";
|
|
5
6
|
import { RuntimeInterceptor } from "./runtime-interceptor.js";
|
|
6
7
|
import {
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
8
|
+
GetErrorsParamsSchema,
|
|
9
|
+
GetPerformanceParamsSchema,
|
|
10
|
+
InspectRequestParamsSchema,
|
|
11
|
+
SearchLogsParamsSchema,
|
|
12
|
+
TailLogsParamsSchema,
|
|
12
13
|
} from "./types.js";
|
|
13
14
|
|
|
14
15
|
export class RuntimeLensMCPServer {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
16
|
+
private readonly server: McpServer;
|
|
17
|
+
private readonly collector: LogCollector;
|
|
18
|
+
private readonly inspector: ProcessInspector;
|
|
19
|
+
private readonly interceptor: RuntimeInterceptor;
|
|
20
|
+
private readonly agentBridge: AgentBridge;
|
|
19
21
|
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
22
|
+
constructor(projectRoot?: string, logPaths?: string[]) {
|
|
23
|
+
this.server = new McpServer({
|
|
24
|
+
name: "runtime-lens-mcp",
|
|
25
|
+
version: "1.1.0",
|
|
26
|
+
});
|
|
27
|
+
this.collector = new LogCollector(projectRoot, logPaths);
|
|
28
|
+
this.inspector = new ProcessInspector(projectRoot);
|
|
29
|
+
this.interceptor = new RuntimeInterceptor(this.collector);
|
|
30
|
+
this.agentBridge = new AgentBridge(this.collector);
|
|
31
|
+
this.setupTools();
|
|
32
|
+
}
|
|
25
33
|
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
34
|
+
static fromEnvironment(): RuntimeLensMCPServer {
|
|
35
|
+
const projectRoot = process.env.RUNTIME_LENS_PROJECT_ROOT || process.cwd();
|
|
36
|
+
const logPaths =
|
|
37
|
+
process.env.RUNTIME_LENS_LOG_PATHS?.split(",").filter(Boolean) || [];
|
|
38
|
+
return new RuntimeLensMCPServer(projectRoot, logPaths);
|
|
39
|
+
}
|
|
29
40
|
|
|
30
|
-
|
|
31
|
-
|
|
41
|
+
private setupTools(): void {
|
|
42
|
+
this.registerTailLogs();
|
|
43
|
+
this.registerSearchLogs();
|
|
44
|
+
this.registerGetErrors();
|
|
45
|
+
this.registerInspectRequests();
|
|
46
|
+
this.registerGetPerformance();
|
|
47
|
+
this.registerGetEnvInfo();
|
|
48
|
+
this.registerClearLogs();
|
|
49
|
+
this.registerGetStats();
|
|
50
|
+
this.registerStartInterceptor();
|
|
51
|
+
this.registerStopInterceptor();
|
|
52
|
+
this.registerCollectLogs();
|
|
53
|
+
this.registerScanProject();
|
|
54
|
+
this.registerFindProcesses();
|
|
55
|
+
this.registerGetPorts();
|
|
56
|
+
}
|
|
32
57
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
58
|
+
private registerTailLogs(): void {
|
|
59
|
+
this.server.registerTool(
|
|
60
|
+
"tail_logs",
|
|
61
|
+
{
|
|
62
|
+
title: "Tail Logs",
|
|
63
|
+
description:
|
|
64
|
+
"Retrieve recent log entries from the application buffer. Supports filtering by level, framework, and source.",
|
|
65
|
+
inputSchema: {
|
|
66
|
+
lines: TailLogsParamsSchema.shape.lines,
|
|
67
|
+
level: TailLogsParamsSchema.shape.level,
|
|
68
|
+
framework: TailLogsParamsSchema.shape.framework,
|
|
69
|
+
source: TailLogsParamsSchema.shape.source,
|
|
70
|
+
},
|
|
71
|
+
},
|
|
72
|
+
async (params) => ({
|
|
73
|
+
content: [
|
|
74
|
+
{
|
|
75
|
+
type: "text" as const,
|
|
76
|
+
text: JSON.stringify(this.collector.getLogs(params), null, 2),
|
|
77
|
+
},
|
|
78
|
+
],
|
|
79
|
+
}),
|
|
80
|
+
);
|
|
81
|
+
}
|
|
38
82
|
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
83
|
+
private registerSearchLogs(): void {
|
|
84
|
+
this.server.registerTool(
|
|
85
|
+
"search_logs",
|
|
86
|
+
{
|
|
87
|
+
title: "Search Logs",
|
|
88
|
+
description:
|
|
89
|
+
"Search through collected logs using regex patterns. Filter by level, framework, and time range.",
|
|
90
|
+
inputSchema: {
|
|
91
|
+
query: SearchLogsParamsSchema.shape.query,
|
|
92
|
+
level: SearchLogsParamsSchema.shape.level,
|
|
93
|
+
framework: SearchLogsParamsSchema.shape.framework,
|
|
94
|
+
limit: SearchLogsParamsSchema.shape.limit,
|
|
95
|
+
since: SearchLogsParamsSchema.shape.since,
|
|
96
|
+
},
|
|
97
|
+
},
|
|
98
|
+
async (params) => ({
|
|
99
|
+
content: [
|
|
100
|
+
{
|
|
101
|
+
type: "text" as const,
|
|
102
|
+
text: JSON.stringify(
|
|
103
|
+
this.collector.searchLogs(params as any),
|
|
104
|
+
null,
|
|
105
|
+
2,
|
|
106
|
+
),
|
|
107
|
+
},
|
|
108
|
+
],
|
|
109
|
+
}),
|
|
110
|
+
);
|
|
111
|
+
}
|
|
55
112
|
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
}
|
|
113
|
+
private registerGetErrors(): void {
|
|
114
|
+
this.server.registerTool(
|
|
115
|
+
"get_errors",
|
|
116
|
+
{
|
|
117
|
+
title: "Get Errors",
|
|
118
|
+
description:
|
|
119
|
+
"Retrieve recent errors with stack traces. Optionally group similar errors together to identify patterns.",
|
|
120
|
+
inputSchema: {
|
|
121
|
+
limit: GetErrorsParamsSchema.shape.limit,
|
|
122
|
+
framework: GetErrorsParamsSchema.shape.framework,
|
|
123
|
+
grouped: GetErrorsParamsSchema.shape.grouped,
|
|
124
|
+
},
|
|
125
|
+
},
|
|
126
|
+
async (params) => ({
|
|
127
|
+
content: [
|
|
128
|
+
{
|
|
129
|
+
type: "text" as const,
|
|
130
|
+
text: JSON.stringify(this.collector.getErrors(params), null, 2),
|
|
131
|
+
},
|
|
132
|
+
],
|
|
133
|
+
}),
|
|
134
|
+
);
|
|
135
|
+
}
|
|
80
136
|
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
137
|
+
private registerInspectRequests(): void {
|
|
138
|
+
this.server.registerTool(
|
|
139
|
+
"inspect_requests",
|
|
140
|
+
{
|
|
141
|
+
title: "Inspect HTTP Requests",
|
|
142
|
+
description:
|
|
143
|
+
"Inspect captured HTTP requests and responses. Filter by method, URL pattern, status code, or specific request ID.",
|
|
144
|
+
inputSchema: {
|
|
145
|
+
id: InspectRequestParamsSchema.shape.id,
|
|
146
|
+
method: InspectRequestParamsSchema.shape.method,
|
|
147
|
+
urlPattern: InspectRequestParamsSchema.shape.urlPattern,
|
|
148
|
+
statusCode: InspectRequestParamsSchema.shape.statusCode,
|
|
149
|
+
limit: InspectRequestParamsSchema.shape.limit,
|
|
150
|
+
},
|
|
151
|
+
},
|
|
152
|
+
async (params) => ({
|
|
153
|
+
content: [
|
|
154
|
+
{
|
|
155
|
+
type: "text" as const,
|
|
156
|
+
text: JSON.stringify(this.collector.getRequests(params), null, 2),
|
|
157
|
+
},
|
|
158
|
+
],
|
|
159
|
+
}),
|
|
160
|
+
);
|
|
161
|
+
}
|
|
106
162
|
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
163
|
+
private registerGetPerformance(): void {
|
|
164
|
+
this.server.registerTool(
|
|
165
|
+
"get_performance",
|
|
166
|
+
{
|
|
167
|
+
title: "Get Performance Metrics",
|
|
168
|
+
description:
|
|
169
|
+
"Retrieve performance metrics including memory usage, CPU, and custom metrics from the application.",
|
|
170
|
+
inputSchema: {
|
|
171
|
+
metric: GetPerformanceParamsSchema.shape.metric,
|
|
172
|
+
since: GetPerformanceParamsSchema.shape.since,
|
|
173
|
+
limit: GetPerformanceParamsSchema.shape.limit,
|
|
174
|
+
},
|
|
175
|
+
},
|
|
176
|
+
async (params) => {
|
|
177
|
+
await this.collector.collectFromProcess();
|
|
178
|
+
return {
|
|
179
|
+
content: [
|
|
180
|
+
{
|
|
181
|
+
type: "text" as const,
|
|
182
|
+
text: JSON.stringify(this.collector.getMetrics(params), null, 2),
|
|
183
|
+
},
|
|
184
|
+
],
|
|
185
|
+
};
|
|
186
|
+
},
|
|
187
|
+
);
|
|
188
|
+
}
|
|
130
189
|
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
);
|
|
155
|
-
}
|
|
190
|
+
private registerGetEnvInfo(): void {
|
|
191
|
+
this.server.registerTool(
|
|
192
|
+
"get_env_info",
|
|
193
|
+
{
|
|
194
|
+
title: "Get Environment Info",
|
|
195
|
+
description:
|
|
196
|
+
"Get comprehensive environment information including running Node.js processes, listening ports, project framework detection, and system resources.",
|
|
197
|
+
inputSchema: {},
|
|
198
|
+
},
|
|
199
|
+
async () => ({
|
|
200
|
+
content: [
|
|
201
|
+
{
|
|
202
|
+
type: "text" as const,
|
|
203
|
+
text: JSON.stringify(
|
|
204
|
+
await this.inspector.getEnvironmentInfo(),
|
|
205
|
+
null,
|
|
206
|
+
2,
|
|
207
|
+
),
|
|
208
|
+
},
|
|
209
|
+
],
|
|
210
|
+
}),
|
|
211
|
+
);
|
|
212
|
+
}
|
|
156
213
|
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
214
|
+
private registerClearLogs(): void {
|
|
215
|
+
this.server.registerTool(
|
|
216
|
+
"clear_logs",
|
|
217
|
+
{
|
|
218
|
+
title: "Clear Log Buffer",
|
|
219
|
+
description:
|
|
220
|
+
"Clear all collected logs, requests, and metrics from the buffer.",
|
|
221
|
+
inputSchema: {},
|
|
222
|
+
},
|
|
223
|
+
async () => {
|
|
224
|
+
const result = this.collector.clearLogs();
|
|
225
|
+
return {
|
|
226
|
+
content: [
|
|
227
|
+
{
|
|
228
|
+
type: "text" as const,
|
|
229
|
+
text: JSON.stringify({
|
|
230
|
+
message: `Cleared ${result.cleared} entries`,
|
|
231
|
+
}),
|
|
232
|
+
},
|
|
233
|
+
],
|
|
234
|
+
};
|
|
235
|
+
},
|
|
236
|
+
);
|
|
237
|
+
}
|
|
181
238
|
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
239
|
+
private registerGetStats(): void {
|
|
240
|
+
this.server.registerTool(
|
|
241
|
+
"get_stats",
|
|
242
|
+
{
|
|
243
|
+
title: "Get Log Statistics",
|
|
244
|
+
description:
|
|
245
|
+
"Get statistics about collected logs including counts by level and framework.",
|
|
246
|
+
inputSchema: {},
|
|
247
|
+
},
|
|
248
|
+
async () => ({
|
|
249
|
+
content: [
|
|
250
|
+
{
|
|
251
|
+
type: "text" as const,
|
|
252
|
+
text: JSON.stringify(this.collector.getStats(), null, 2),
|
|
253
|
+
},
|
|
254
|
+
],
|
|
255
|
+
}),
|
|
256
|
+
);
|
|
257
|
+
}
|
|
201
258
|
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
259
|
+
private registerStartInterceptor(): void {
|
|
260
|
+
this.server.registerTool(
|
|
261
|
+
"start_interceptor",
|
|
262
|
+
{
|
|
263
|
+
title: "Start Console Interceptor",
|
|
264
|
+
description:
|
|
265
|
+
"Start intercepting console.log/warn/error/debug calls and stderr output in real-time. Captured output is stored in the log buffer.",
|
|
266
|
+
inputSchema: {},
|
|
267
|
+
},
|
|
268
|
+
async () => {
|
|
269
|
+
this.interceptor.startIntercepting();
|
|
270
|
+
return {
|
|
271
|
+
content: [
|
|
272
|
+
{
|
|
273
|
+
type: "text" as const,
|
|
274
|
+
text: JSON.stringify({
|
|
275
|
+
message: "Console interceptor started",
|
|
276
|
+
active: true,
|
|
277
|
+
}),
|
|
278
|
+
},
|
|
279
|
+
],
|
|
280
|
+
};
|
|
281
|
+
},
|
|
282
|
+
);
|
|
283
|
+
}
|
|
221
284
|
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
285
|
+
private registerStopInterceptor(): void {
|
|
286
|
+
this.server.registerTool(
|
|
287
|
+
"stop_interceptor",
|
|
288
|
+
{
|
|
289
|
+
title: "Stop Console Interceptor",
|
|
290
|
+
description:
|
|
291
|
+
"Stop intercepting console output. Previously captured logs remain in the buffer.",
|
|
292
|
+
inputSchema: {},
|
|
293
|
+
},
|
|
294
|
+
async () => {
|
|
295
|
+
this.interceptor.stopIntercepting();
|
|
296
|
+
return {
|
|
297
|
+
content: [
|
|
298
|
+
{
|
|
299
|
+
type: "text" as const,
|
|
300
|
+
text: JSON.stringify({
|
|
301
|
+
message: "Console interceptor stopped",
|
|
302
|
+
active: false,
|
|
303
|
+
}),
|
|
304
|
+
},
|
|
305
|
+
],
|
|
306
|
+
};
|
|
307
|
+
},
|
|
308
|
+
);
|
|
309
|
+
}
|
|
241
310
|
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
311
|
+
private registerCollectLogs(): void {
|
|
312
|
+
this.server.registerTool(
|
|
313
|
+
"collect_from_files",
|
|
314
|
+
{
|
|
315
|
+
title: "Collect Logs from Files",
|
|
316
|
+
description:
|
|
317
|
+
"Scan and collect logs from log files in the project directory. Automatically discovers .log and .json files in common log directories.",
|
|
318
|
+
inputSchema: {},
|
|
319
|
+
},
|
|
320
|
+
async () => {
|
|
321
|
+
await this.collector.collectFromFiles();
|
|
322
|
+
return {
|
|
323
|
+
content: [
|
|
324
|
+
{
|
|
325
|
+
type: "text" as const,
|
|
326
|
+
text: JSON.stringify({
|
|
327
|
+
message: "Log collection complete",
|
|
328
|
+
stats: this.collector.getStats(),
|
|
329
|
+
}),
|
|
330
|
+
},
|
|
331
|
+
],
|
|
332
|
+
};
|
|
333
|
+
},
|
|
334
|
+
);
|
|
335
|
+
}
|
|
261
336
|
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
337
|
+
private registerScanProject(): void {
|
|
338
|
+
this.server.registerTool(
|
|
339
|
+
"scan_project",
|
|
340
|
+
{
|
|
341
|
+
title: "Scan Project Structure",
|
|
342
|
+
description:
|
|
343
|
+
"Analyze the project to detect framework (React/Next.js/NestJS), find log files, and list configuration files.",
|
|
344
|
+
inputSchema: {},
|
|
345
|
+
},
|
|
346
|
+
async () => ({
|
|
347
|
+
content: [
|
|
348
|
+
{
|
|
349
|
+
type: "text" as const,
|
|
350
|
+
text: JSON.stringify(
|
|
351
|
+
await this.collector.scanProjectStructure(),
|
|
352
|
+
null,
|
|
353
|
+
2,
|
|
354
|
+
),
|
|
355
|
+
},
|
|
356
|
+
],
|
|
357
|
+
}),
|
|
358
|
+
);
|
|
359
|
+
}
|
|
281
360
|
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
361
|
+
private registerFindProcesses(): void {
|
|
362
|
+
this.server.registerTool(
|
|
363
|
+
"find_processes",
|
|
364
|
+
{
|
|
365
|
+
title: "Find Running Node Processes",
|
|
366
|
+
description:
|
|
367
|
+
"Find running Node.js processes related to React, Next.js, or NestJS applications.",
|
|
368
|
+
inputSchema: {},
|
|
369
|
+
},
|
|
370
|
+
async () => ({
|
|
371
|
+
content: [
|
|
372
|
+
{
|
|
373
|
+
type: "text" as const,
|
|
374
|
+
text: JSON.stringify(
|
|
375
|
+
await this.inspector.findRunningProcesses(),
|
|
376
|
+
null,
|
|
377
|
+
2,
|
|
378
|
+
),
|
|
379
|
+
},
|
|
380
|
+
],
|
|
381
|
+
}),
|
|
382
|
+
);
|
|
383
|
+
}
|
|
302
384
|
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
385
|
+
private registerGetPorts(): void {
|
|
386
|
+
this.server.registerTool(
|
|
387
|
+
"get_listening_ports",
|
|
388
|
+
{
|
|
389
|
+
title: "Get Listening Ports",
|
|
390
|
+
description:
|
|
391
|
+
"List all TCP ports currently being listened on by Node.js processes.",
|
|
392
|
+
inputSchema: {},
|
|
393
|
+
},
|
|
394
|
+
async () => ({
|
|
395
|
+
content: [
|
|
396
|
+
{
|
|
397
|
+
type: "text" as const,
|
|
398
|
+
text: JSON.stringify(
|
|
399
|
+
await this.inspector.getPortListeners(),
|
|
400
|
+
null,
|
|
401
|
+
2,
|
|
402
|
+
),
|
|
403
|
+
},
|
|
404
|
+
],
|
|
405
|
+
}),
|
|
406
|
+
);
|
|
407
|
+
}
|
|
322
408
|
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
}],
|
|
338
|
-
};
|
|
339
|
-
}
|
|
340
|
-
);
|
|
341
|
-
}
|
|
409
|
+
async start(): Promise<void> {
|
|
410
|
+
try {
|
|
411
|
+
this.agentBridge.connect();
|
|
412
|
+
const transport = new StdioServerTransport();
|
|
413
|
+
await this.server.connect(transport);
|
|
414
|
+
console.error("Runtime Lens MCP Server started successfully");
|
|
415
|
+
} catch (error) {
|
|
416
|
+
console.error(
|
|
417
|
+
"Failed to start Runtime Lens MCP Server:",
|
|
418
|
+
error instanceof Error ? error.message : error,
|
|
419
|
+
);
|
|
420
|
+
process.exit(1);
|
|
421
|
+
}
|
|
422
|
+
}
|
|
342
423
|
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
return {
|
|
354
|
-
content: [{
|
|
355
|
-
type: "text" as const,
|
|
356
|
-
text: JSON.stringify(ports, null, 2),
|
|
357
|
-
}],
|
|
358
|
-
};
|
|
359
|
-
}
|
|
360
|
-
);
|
|
361
|
-
}
|
|
362
|
-
|
|
363
|
-
async start(): Promise<void> {
|
|
364
|
-
try {
|
|
365
|
-
const transport = new StdioServerTransport();
|
|
366
|
-
await this.server.connect(transport);
|
|
367
|
-
console.error("Runtime Lens MCP Server started successfully");
|
|
368
|
-
} catch (error) {
|
|
369
|
-
console.error(
|
|
370
|
-
"Failed to start Runtime Lens MCP Server:",
|
|
371
|
-
error instanceof Error ? error.message : error
|
|
372
|
-
);
|
|
373
|
-
process.exit(1);
|
|
374
|
-
}
|
|
375
|
-
}
|
|
376
|
-
|
|
377
|
-
setupGracefulShutdown(): void {
|
|
378
|
-
const shutdown = async (signal: string): Promise<void> => {
|
|
379
|
-
console.error(`Received ${signal}, shutting down gracefully...`);
|
|
380
|
-
this.interceptor.stopIntercepting();
|
|
381
|
-
process.exit(0);
|
|
382
|
-
};
|
|
383
|
-
|
|
384
|
-
process.on("SIGINT", () => shutdown("SIGINT"));
|
|
385
|
-
process.on("SIGTERM", () => shutdown("SIGTERM"));
|
|
386
|
-
}
|
|
424
|
+
setupGracefulShutdown(): void {
|
|
425
|
+
const shutdown = async (signal: string): Promise<void> => {
|
|
426
|
+
console.error(`Received ${signal}, shutting down gracefully...`);
|
|
427
|
+
this.agentBridge.disconnect();
|
|
428
|
+
this.interceptor.stopIntercepting();
|
|
429
|
+
process.exit(0);
|
|
430
|
+
};
|
|
431
|
+
process.on("SIGINT", () => shutdown("SIGINT"));
|
|
432
|
+
process.on("SIGTERM", () => shutdown("SIGTERM"));
|
|
433
|
+
}
|
|
387
434
|
}
|