@0x1f320.sh/why-did-you-render-mcp 1.0.0-dev.2 → 1.0.0-dev.4
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/dist/client/index.cjs +39 -10
- package/dist/client/index.js +39 -10
- package/dist/server/index.js +17 -6
- package/package.json +1 -1
package/dist/client/index.cjs
CHANGED
|
@@ -50,21 +50,27 @@ function patchDevToolsHook(onCommit) {
|
|
|
50
50
|
function buildOptions(opts) {
|
|
51
51
|
const wsUrl = opts?.wsUrl ?? DEFAULT_WS_URL;
|
|
52
52
|
const projectId = opts?.projectId ?? globalThis.location?.origin ?? "default";
|
|
53
|
+
const MAX_QUEUE_SIZE = 1e3;
|
|
54
|
+
const BASE_DELAY = 1e3;
|
|
55
|
+
const MAX_DELAY = 3e4;
|
|
53
56
|
let ws = null;
|
|
54
57
|
let queue = [];
|
|
55
58
|
let commitId = 0;
|
|
59
|
+
let retryDelay = BASE_DELAY;
|
|
56
60
|
patchDevToolsHook(() => {
|
|
57
61
|
commitId++;
|
|
58
62
|
});
|
|
59
63
|
function connect() {
|
|
60
64
|
ws = new WebSocket(wsUrl);
|
|
61
65
|
ws.addEventListener("open", () => {
|
|
66
|
+
retryDelay = BASE_DELAY;
|
|
62
67
|
for (const msg of queue) ws?.send(JSON.stringify(msg));
|
|
63
68
|
queue = [];
|
|
64
69
|
});
|
|
65
70
|
ws.addEventListener("close", () => {
|
|
66
71
|
ws = null;
|
|
67
|
-
setTimeout(connect,
|
|
72
|
+
setTimeout(connect, retryDelay);
|
|
73
|
+
retryDelay = Math.min(retryDelay * 2, MAX_DELAY);
|
|
68
74
|
});
|
|
69
75
|
ws.addEventListener("error", () => {
|
|
70
76
|
ws?.close();
|
|
@@ -73,19 +79,42 @@ function buildOptions(opts) {
|
|
|
73
79
|
connect();
|
|
74
80
|
function send(msg) {
|
|
75
81
|
if (ws?.readyState === WebSocket.OPEN) ws.send(JSON.stringify(msg));
|
|
76
|
-
else
|
|
82
|
+
else {
|
|
83
|
+
if (queue.length >= MAX_QUEUE_SIZE) queue.shift();
|
|
84
|
+
queue.push(msg);
|
|
85
|
+
}
|
|
77
86
|
}
|
|
78
|
-
|
|
87
|
+
let pendingBatch = null;
|
|
88
|
+
let flushScheduled = false;
|
|
89
|
+
function flushBatch() {
|
|
90
|
+
flushScheduled = false;
|
|
91
|
+
if (!pendingBatch || pendingBatch.reports.length === 0) return;
|
|
79
92
|
send({
|
|
80
|
-
type: "render",
|
|
93
|
+
type: "render-batch",
|
|
81
94
|
projectId,
|
|
82
|
-
commitId,
|
|
83
|
-
payload:
|
|
84
|
-
displayName: info.displayName,
|
|
85
|
-
reason: sanitizeReason(info.reason),
|
|
86
|
-
hookName: info.hookName
|
|
87
|
-
}
|
|
95
|
+
commitId: pendingBatch.commitId,
|
|
96
|
+
payload: pendingBatch.reports
|
|
88
97
|
});
|
|
98
|
+
pendingBatch = null;
|
|
99
|
+
}
|
|
100
|
+
return { notifier(info) {
|
|
101
|
+
const report = {
|
|
102
|
+
displayName: info.displayName,
|
|
103
|
+
reason: sanitizeReason(info.reason),
|
|
104
|
+
hookName: info.hookName
|
|
105
|
+
};
|
|
106
|
+
if (pendingBatch && pendingBatch.commitId === commitId) pendingBatch.reports.push(report);
|
|
107
|
+
else {
|
|
108
|
+
if (pendingBatch) flushBatch();
|
|
109
|
+
pendingBatch = {
|
|
110
|
+
commitId,
|
|
111
|
+
reports: [report]
|
|
112
|
+
};
|
|
113
|
+
}
|
|
114
|
+
if (!flushScheduled) {
|
|
115
|
+
flushScheduled = true;
|
|
116
|
+
queueMicrotask(flushBatch);
|
|
117
|
+
}
|
|
89
118
|
} };
|
|
90
119
|
}
|
|
91
120
|
//#endregion
|
package/dist/client/index.js
CHANGED
|
@@ -49,21 +49,27 @@ function patchDevToolsHook(onCommit) {
|
|
|
49
49
|
function buildOptions(opts) {
|
|
50
50
|
const wsUrl = opts?.wsUrl ?? DEFAULT_WS_URL;
|
|
51
51
|
const projectId = opts?.projectId ?? globalThis.location?.origin ?? "default";
|
|
52
|
+
const MAX_QUEUE_SIZE = 1e3;
|
|
53
|
+
const BASE_DELAY = 1e3;
|
|
54
|
+
const MAX_DELAY = 3e4;
|
|
52
55
|
let ws = null;
|
|
53
56
|
let queue = [];
|
|
54
57
|
let commitId = 0;
|
|
58
|
+
let retryDelay = BASE_DELAY;
|
|
55
59
|
patchDevToolsHook(() => {
|
|
56
60
|
commitId++;
|
|
57
61
|
});
|
|
58
62
|
function connect() {
|
|
59
63
|
ws = new WebSocket(wsUrl);
|
|
60
64
|
ws.addEventListener("open", () => {
|
|
65
|
+
retryDelay = BASE_DELAY;
|
|
61
66
|
for (const msg of queue) ws?.send(JSON.stringify(msg));
|
|
62
67
|
queue = [];
|
|
63
68
|
});
|
|
64
69
|
ws.addEventListener("close", () => {
|
|
65
70
|
ws = null;
|
|
66
|
-
setTimeout(connect,
|
|
71
|
+
setTimeout(connect, retryDelay);
|
|
72
|
+
retryDelay = Math.min(retryDelay * 2, MAX_DELAY);
|
|
67
73
|
});
|
|
68
74
|
ws.addEventListener("error", () => {
|
|
69
75
|
ws?.close();
|
|
@@ -72,19 +78,42 @@ function buildOptions(opts) {
|
|
|
72
78
|
connect();
|
|
73
79
|
function send(msg) {
|
|
74
80
|
if (ws?.readyState === WebSocket.OPEN) ws.send(JSON.stringify(msg));
|
|
75
|
-
else
|
|
81
|
+
else {
|
|
82
|
+
if (queue.length >= MAX_QUEUE_SIZE) queue.shift();
|
|
83
|
+
queue.push(msg);
|
|
84
|
+
}
|
|
76
85
|
}
|
|
77
|
-
|
|
86
|
+
let pendingBatch = null;
|
|
87
|
+
let flushScheduled = false;
|
|
88
|
+
function flushBatch() {
|
|
89
|
+
flushScheduled = false;
|
|
90
|
+
if (!pendingBatch || pendingBatch.reports.length === 0) return;
|
|
78
91
|
send({
|
|
79
|
-
type: "render",
|
|
92
|
+
type: "render-batch",
|
|
80
93
|
projectId,
|
|
81
|
-
commitId,
|
|
82
|
-
payload:
|
|
83
|
-
displayName: info.displayName,
|
|
84
|
-
reason: sanitizeReason(info.reason),
|
|
85
|
-
hookName: info.hookName
|
|
86
|
-
}
|
|
94
|
+
commitId: pendingBatch.commitId,
|
|
95
|
+
payload: pendingBatch.reports
|
|
87
96
|
});
|
|
97
|
+
pendingBatch = null;
|
|
98
|
+
}
|
|
99
|
+
return { notifier(info) {
|
|
100
|
+
const report = {
|
|
101
|
+
displayName: info.displayName,
|
|
102
|
+
reason: sanitizeReason(info.reason),
|
|
103
|
+
hookName: info.hookName
|
|
104
|
+
};
|
|
105
|
+
if (pendingBatch && pendingBatch.commitId === commitId) pendingBatch.reports.push(report);
|
|
106
|
+
else {
|
|
107
|
+
if (pendingBatch) flushBatch();
|
|
108
|
+
pendingBatch = {
|
|
109
|
+
commitId,
|
|
110
|
+
reports: [report]
|
|
111
|
+
};
|
|
112
|
+
}
|
|
113
|
+
if (!flushScheduled) {
|
|
114
|
+
flushScheduled = true;
|
|
115
|
+
queueMicrotask(flushBatch);
|
|
116
|
+
}
|
|
88
117
|
} };
|
|
89
118
|
}
|
|
90
119
|
//#endregion
|
package/dist/server/index.js
CHANGED
|
@@ -344,11 +344,10 @@ function createWsServer(port) {
|
|
|
344
344
|
ws.on("message", (raw) => {
|
|
345
345
|
try {
|
|
346
346
|
const msg = JSON.parse(String(raw));
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
}
|
|
347
|
+
const projectId = msg.projectId ?? "default";
|
|
348
|
+
heartbeat.setProjectId(ws, projectId);
|
|
349
|
+
if (msg.type === "render") store.addRender(msg.payload, projectId, msg.commitId);
|
|
350
|
+
else if (msg.type === "render-batch") for (const report of msg.payload) store.addRender(report, projectId, msg.commitId);
|
|
352
351
|
} catch {
|
|
353
352
|
console.error("[wdyr-mcp] invalid message received");
|
|
354
353
|
}
|
|
@@ -371,10 +370,22 @@ const server = new McpServer({
|
|
|
371
370
|
});
|
|
372
371
|
registerTools(server);
|
|
373
372
|
async function main() {
|
|
374
|
-
createWsServer(Number(process.env.WDYR_WS_PORT) || DEFAULT_WS_PORT);
|
|
373
|
+
const wss = createWsServer(Number(process.env.WDYR_WS_PORT) || DEFAULT_WS_PORT);
|
|
375
374
|
const transport = new StdioServerTransport();
|
|
376
375
|
await server.connect(transport);
|
|
377
376
|
console.error("[wdyr-mcp] MCP server running on stdio");
|
|
377
|
+
let shuttingDown = false;
|
|
378
|
+
async function shutdown() {
|
|
379
|
+
if (shuttingDown) return;
|
|
380
|
+
shuttingDown = true;
|
|
381
|
+
console.error("[wdyr-mcp] Shutting down…");
|
|
382
|
+
wss?.close();
|
|
383
|
+
await server.close();
|
|
384
|
+
process.exit(0);
|
|
385
|
+
}
|
|
386
|
+
process.stdin.on("end", shutdown);
|
|
387
|
+
process.on("SIGTERM", shutdown);
|
|
388
|
+
process.on("SIGINT", shutdown);
|
|
378
389
|
}
|
|
379
390
|
main().catch((error) => {
|
|
380
391
|
console.error("[wdyr-mcp] Fatal error:", error);
|
package/package.json
CHANGED