@ethisyscore/extension-runtime 1.70.0 → 1.71.1
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/host/index.cjs +129 -7
- package/dist/host/index.cjs.map +1 -1
- package/dist/host/index.d.cts +3 -2
- package/dist/host/index.d.ts +3 -2
- package/dist/host/index.js +122 -8
- package/dist/host/index.js.map +1 -1
- package/dist/index.cjs +104 -0
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +97 -1
- package/dist/index.js.map +1 -1
- package/dist/mcp-error-CCZQd8Xl.d.cts +118 -0
- package/dist/mcp-error-CCZQd8Xl.d.ts +118 -0
- package/dist/mock-host/cli.cjs +84 -4
- package/dist/mock-host/cli.cjs.map +1 -1
- package/dist/mock-host/cli.d.cts +1 -1
- package/dist/mock-host/cli.d.ts +1 -1
- package/dist/mock-host/cli.js +84 -4
- package/dist/mock-host/cli.js.map +1 -1
- package/dist/plugin/index.cjs +106 -5
- package/dist/plugin/index.cjs.map +1 -1
- package/dist/plugin/index.d.cts +1 -0
- package/dist/plugin/index.d.ts +1 -0
- package/dist/plugin/index.js +99 -6
- package/dist/plugin/index.js.map +1 -1
- package/dist/{transport-BPwasdNz.d.ts → transport-BuX8gzq1.d.ts} +7 -0
- package/dist/{transport-BbSPAS_N.d.cts → transport-C4xoMWBE.d.cts} +7 -0
- package/package.json +2 -2
package/dist/host/index.cjs
CHANGED
|
@@ -287,6 +287,100 @@ function createInputEventCoalescer(sink, options = {}) {
|
|
|
287
287
|
};
|
|
288
288
|
}
|
|
289
289
|
|
|
290
|
+
// src/bridge/mcp-error.ts
|
|
291
|
+
var MCP_ERROR_CODES = [
|
|
292
|
+
"unauthorized",
|
|
293
|
+
"forbidden",
|
|
294
|
+
"not_found",
|
|
295
|
+
"invalid_request",
|
|
296
|
+
"conflict",
|
|
297
|
+
"rate_limited",
|
|
298
|
+
"timeout",
|
|
299
|
+
"unavailable",
|
|
300
|
+
"internal"
|
|
301
|
+
];
|
|
302
|
+
function isMcpErrorCode(value) {
|
|
303
|
+
return typeof value === "string" && MCP_ERROR_CODES.includes(value);
|
|
304
|
+
}
|
|
305
|
+
var RETRYABLE = ["rate_limited", "timeout", "unavailable"];
|
|
306
|
+
function isRetryableMcpErrorCode(code) {
|
|
307
|
+
return RETRYABLE.includes(code);
|
|
308
|
+
}
|
|
309
|
+
var McpToolError = class extends Error {
|
|
310
|
+
/** Machine-readable classification. `internal` when the host sent none. */
|
|
311
|
+
code;
|
|
312
|
+
/**
|
|
313
|
+
* Marks the instance for {@link isMcpToolError}. A structural marker rather than a prototype
|
|
314
|
+
* check because the error can be constructed in one bundle and inspected in another, where
|
|
315
|
+
* `instanceof` compares two different class objects and answers false.
|
|
316
|
+
*/
|
|
317
|
+
isMcpToolError = true;
|
|
318
|
+
constructor(message, code = "internal") {
|
|
319
|
+
super(message);
|
|
320
|
+
this.name = "McpHostError";
|
|
321
|
+
this.code = code;
|
|
322
|
+
}
|
|
323
|
+
/** True when this failure is worth retrying unchanged. */
|
|
324
|
+
get retryable() {
|
|
325
|
+
return isRetryableMcpErrorCode(this.code);
|
|
326
|
+
}
|
|
327
|
+
};
|
|
328
|
+
function isMcpToolError(value) {
|
|
329
|
+
return value instanceof McpToolError || value !== null && typeof value === "object" && value.isMcpToolError === true && isMcpErrorCode(value.code);
|
|
330
|
+
}
|
|
331
|
+
function mcpErrorCodeFromHttpStatus(status) {
|
|
332
|
+
switch (status) {
|
|
333
|
+
case 401:
|
|
334
|
+
return "unauthorized";
|
|
335
|
+
case 403:
|
|
336
|
+
return "forbidden";
|
|
337
|
+
case 404:
|
|
338
|
+
return "not_found";
|
|
339
|
+
case 400:
|
|
340
|
+
case 422:
|
|
341
|
+
return "invalid_request";
|
|
342
|
+
case 409:
|
|
343
|
+
case 412:
|
|
344
|
+
return "conflict";
|
|
345
|
+
case 429:
|
|
346
|
+
return "rate_limited";
|
|
347
|
+
case 408:
|
|
348
|
+
case 504:
|
|
349
|
+
return "timeout";
|
|
350
|
+
case 502:
|
|
351
|
+
case 503:
|
|
352
|
+
return "unavailable";
|
|
353
|
+
default:
|
|
354
|
+
return "internal";
|
|
355
|
+
}
|
|
356
|
+
}
|
|
357
|
+
function classifyHostResponse(response) {
|
|
358
|
+
if (response.ok) {
|
|
359
|
+
return void 0;
|
|
360
|
+
}
|
|
361
|
+
if (isMcpErrorCode(response.mcpErrorCode)) {
|
|
362
|
+
return response.mcpErrorCode;
|
|
363
|
+
}
|
|
364
|
+
return typeof response.status === "number" ? mcpErrorCodeFromHttpStatus(response.status) : "internal";
|
|
365
|
+
}
|
|
366
|
+
function classifyHostError(err) {
|
|
367
|
+
if (err === null || typeof err !== "object") {
|
|
368
|
+
return "internal";
|
|
369
|
+
}
|
|
370
|
+
const candidate = err;
|
|
371
|
+
if (isMcpErrorCode(candidate.mcpErrorCode)) {
|
|
372
|
+
return candidate.mcpErrorCode;
|
|
373
|
+
}
|
|
374
|
+
const status = typeof candidate.status === "number" ? candidate.status : typeof candidate.statusCode === "number" ? candidate.statusCode : void 0;
|
|
375
|
+
if (status !== void 0) {
|
|
376
|
+
return mcpErrorCodeFromHttpStatus(status);
|
|
377
|
+
}
|
|
378
|
+
if (candidate.name === "AbortError" || candidate.name === "TimeoutError") {
|
|
379
|
+
return "timeout";
|
|
380
|
+
}
|
|
381
|
+
return "internal";
|
|
382
|
+
}
|
|
383
|
+
|
|
290
384
|
// src/host/version-skew.ts
|
|
291
385
|
var EXTENSION_VERSION_HEADER = "x-extension-version";
|
|
292
386
|
var EXTENSION_ACTIVE_VERSION_HEADER = "x-extension-active-version";
|
|
@@ -713,7 +807,11 @@ var WorkerRemoteDomTransport = class {
|
|
|
713
807
|
type: "ethisys:mcp:invokeTool:result",
|
|
714
808
|
ok: result.ok,
|
|
715
809
|
data: result.data,
|
|
716
|
-
error: result.error
|
|
810
|
+
error: result.error,
|
|
811
|
+
// A client that REPORTS failure rather than throwing lands here, which is the common
|
|
812
|
+
// shape for anything wrapping HTTP. Classifying only the thrown path left these
|
|
813
|
+
// arriving as `internal`.
|
|
814
|
+
code: classifyHostResponse(result)
|
|
717
815
|
});
|
|
718
816
|
} catch (err) {
|
|
719
817
|
this.replyError(message.id, "ethisys:mcp:invokeTool:result", err);
|
|
@@ -743,7 +841,11 @@ var WorkerRemoteDomTransport = class {
|
|
|
743
841
|
type: "ethisys:mcp:getResource:result",
|
|
744
842
|
ok: result.ok,
|
|
745
843
|
data: result.data,
|
|
746
|
-
error: result.error
|
|
844
|
+
error: result.error,
|
|
845
|
+
// A client that REPORTS failure rather than throwing lands here, which is the common
|
|
846
|
+
// shape for anything wrapping HTTP. Classifying only the thrown path left these
|
|
847
|
+
// arriving as `internal`.
|
|
848
|
+
code: classifyHostResponse(result)
|
|
747
849
|
});
|
|
748
850
|
} catch (err) {
|
|
749
851
|
this.replyError(message.id, "ethisys:mcp:getResource:result", err);
|
|
@@ -774,7 +876,11 @@ var WorkerRemoteDomTransport = class {
|
|
|
774
876
|
type: "ethisys:mcp:uploadDocument:result",
|
|
775
877
|
ok: result.ok,
|
|
776
878
|
data: result.data,
|
|
777
|
-
error: result.error
|
|
879
|
+
error: result.error,
|
|
880
|
+
// A client that REPORTS failure rather than throwing lands here, which is the common
|
|
881
|
+
// shape for anything wrapping HTTP. Classifying only the thrown path left these
|
|
882
|
+
// arriving as `internal`.
|
|
883
|
+
code: classifyHostResponse(result)
|
|
778
884
|
});
|
|
779
885
|
} catch (err) {
|
|
780
886
|
this.replyError(message.id, "ethisys:mcp:uploadDocument:result", err);
|
|
@@ -782,7 +888,7 @@ var WorkerRemoteDomTransport = class {
|
|
|
782
888
|
}
|
|
783
889
|
replyError(id, type, err) {
|
|
784
890
|
const message = err instanceof Error ? err.message : "MCP request failed";
|
|
785
|
-
this.safePostMessage({ id, type, ok: false, error: message });
|
|
891
|
+
this.safePostMessage({ id, type, ok: false, error: message, code: classifyHostError(err) });
|
|
786
892
|
}
|
|
787
893
|
};
|
|
788
894
|
var IFRAME_BRIDGE_PROTOCOL = "ethisys.iframe.bridge.v1";
|
|
@@ -988,7 +1094,11 @@ var IframeBridgeTransport = class {
|
|
|
988
1094
|
type: "ethisys:mcp:invokeTool:result",
|
|
989
1095
|
ok: result.ok,
|
|
990
1096
|
data: result.data,
|
|
991
|
-
error: result.error
|
|
1097
|
+
error: result.error,
|
|
1098
|
+
// A client that REPORTS failure rather than throwing lands here, which is the common shape
|
|
1099
|
+
// for anything wrapping HTTP. Classifying only the thrown path left these arriving as
|
|
1100
|
+
// `internal`.
|
|
1101
|
+
code: classifyHostResponse(result)
|
|
992
1102
|
});
|
|
993
1103
|
} catch (err) {
|
|
994
1104
|
this.replyError(message.id, "ethisys:mcp:invokeTool:result", err);
|
|
@@ -1042,7 +1152,11 @@ var IframeBridgeTransport = class {
|
|
|
1042
1152
|
type: "ethisys:mcp:getResource:result",
|
|
1043
1153
|
ok: result.ok,
|
|
1044
1154
|
data: result.data,
|
|
1045
|
-
error: result.error
|
|
1155
|
+
error: result.error,
|
|
1156
|
+
// A client that REPORTS failure rather than throwing lands here, which is the common shape
|
|
1157
|
+
// for anything wrapping HTTP. Classifying only the thrown path left these arriving as
|
|
1158
|
+
// `internal`.
|
|
1159
|
+
code: classifyHostResponse(result)
|
|
1046
1160
|
});
|
|
1047
1161
|
} catch (err) {
|
|
1048
1162
|
this.replyError(message.id, "ethisys:mcp:getResource:result", err);
|
|
@@ -1050,7 +1164,7 @@ var IframeBridgeTransport = class {
|
|
|
1050
1164
|
}
|
|
1051
1165
|
replyError(id, type, err) {
|
|
1052
1166
|
const message = err instanceof Error ? err.message : "MCP request failed";
|
|
1053
|
-
this.safePostMessage({ id, type, ok: false, error: message });
|
|
1167
|
+
this.safePostMessage({ id, type, ok: false, error: message, code: classifyHostError(err) });
|
|
1054
1168
|
}
|
|
1055
1169
|
/** Best-effort reply over the host port; tolerates post-dispose races. */
|
|
1056
1170
|
safePostMessage(message) {
|
|
@@ -1084,14 +1198,22 @@ exports.EXTENSION_ACTIVE_VERSION_HEADER = EXTENSION_ACTIVE_VERSION_HEADER;
|
|
|
1084
1198
|
exports.EXTENSION_VERSION_HEADER = EXTENSION_VERSION_HEADER;
|
|
1085
1199
|
exports.IFRAME_BRIDGE_PROTOCOL = IFRAME_BRIDGE_PROTOCOL;
|
|
1086
1200
|
exports.IframeBridgeTransport = IframeBridgeTransport;
|
|
1201
|
+
exports.MCP_ERROR_CODES = MCP_ERROR_CODES;
|
|
1202
|
+
exports.McpToolError = McpToolError;
|
|
1087
1203
|
exports.SemanticComponentRegistry = SemanticComponentRegistry;
|
|
1088
1204
|
exports.VERSION_MISMATCH_REASON = VERSION_MISMATCH_REASON;
|
|
1089
1205
|
exports.WORKER_TRANSPORT_PROTOCOL = WORKER_TRANSPORT_PROTOCOL;
|
|
1090
1206
|
exports.WorkerRemoteDomTransport = WorkerRemoteDomTransport;
|
|
1207
|
+
exports.classifyHostError = classifyHostError;
|
|
1208
|
+
exports.classifyHostResponse = classifyHostResponse;
|
|
1091
1209
|
exports.createInputEventCoalescer = createInputEventCoalescer;
|
|
1092
1210
|
exports.createOffscreenCanvasTransfer = createOffscreenCanvasTransfer;
|
|
1093
1211
|
exports.detectVersionSkew = detectVersionSkew;
|
|
1094
1212
|
exports.evaluate = evaluate;
|
|
1095
1213
|
exports.interpret = interpret;
|
|
1214
|
+
exports.isMcpErrorCode = isMcpErrorCode;
|
|
1215
|
+
exports.isMcpToolError = isMcpToolError;
|
|
1216
|
+
exports.isRetryableMcpErrorCode = isRetryableMcpErrorCode;
|
|
1217
|
+
exports.mcpErrorCodeFromHttpStatus = mcpErrorCodeFromHttpStatus;
|
|
1096
1218
|
//# sourceMappingURL=index.cjs.map
|
|
1097
1219
|
//# sourceMappingURL=index.cjs.map
|