mirror of
https://github.com/morluto/rea.git
synced 2026-11-02 21:06:04 +00:00
* fix(providers): name JEB, IDA, and one-shot command deadlines Wire JEB catalog discovery to REA_JEB_MCP_TIMEOUT_MS, name the IDA registration timeoutMs, and add command_timeout_ms for one-shot objdump and rizin. Debugger, Frida, and Cutter caps stay fixed and say so. Refs #5910 Co-authored-by: morluto <morluto@users.noreply.github.com> * fix(providers): pass remaining deadlines and name the cap that fired Catalog discovery now sends the JEB budget still remaining to the SDK on connect and every tools/list page. Objdump and rizin preflight share one command_timeout_ms across stat and digest; the command still receives that budget again. Architecture Evidence keeps a selected timeout, and Frida and Rizin name the capture limit that actually stopped output. Co-authored-by: morluto <morluto@users.noreply.github.com> * fix(frida): preserve non-timeout device lookup failures getDeviceById is a lookup deadline only when Frida rejects with "Device not found" after the wait. A device-manager or backend failure stays a capability error. Align the assertions that still expected the previous capacity and capture sentences. Co-authored-by: morluto <morluto@users.noreply.github.com> --------- Co-authored-by: Cursor Agent <cursoragent@cursor.com> Co-authored-by: morluto <morluto@users.noreply.github.com>
70 lines
2.5 KiB
TypeScript
70 lines
2.5 KiB
TypeScript
import { expect, it } from "vitest";
|
|
import { JebProvider } from "../../../src/jeb/JebProvider.js";
|
|
import { createStreamableHttpJebMcpConnection } from "../../../src/jeb/JebMcpConnection.js";
|
|
import { AnalysisTimeoutError } from "../../../src/domain/analysisErrorCore.js";
|
|
import { projectAnalysisError } from "../../../src/domain/analysisErrorProjection.js";
|
|
import {
|
|
startJebMcpFixture,
|
|
jebPrimaryResponses,
|
|
} from "../../fixtures/jebMcp.js";
|
|
|
|
it.each([
|
|
{ operation: "inspect_jeb_client", stage: "catalog" },
|
|
{ operation: "inspect_jeb_client", stage: "tool" },
|
|
{ operation: "list_jeb_units", stage: "catalog" },
|
|
{ operation: "list_jeb_units", stage: "tool" },
|
|
] as const)(
|
|
"attributes a real SDK $stage timeout to $operation",
|
|
async ({ operation, stage }) => {
|
|
let release!: () => void;
|
|
const gate = new Promise<void>((resolve) => {
|
|
release = resolve;
|
|
});
|
|
const fixture = await startJebMcpFixture(
|
|
async (tool) => {
|
|
await gate;
|
|
return jebPrimaryResponses[tool]!;
|
|
},
|
|
stage === "catalog"
|
|
? async () => {
|
|
await gate;
|
|
return { tools: [] };
|
|
}
|
|
: undefined,
|
|
);
|
|
const provider = new JebProvider({
|
|
environment: { REA_JEB_MCP_URL: fixture.endpoint },
|
|
connectionFactory: (endpoint) =>
|
|
createStreamableHttpJebMcpConnection(endpoint, {
|
|
discoveryTimeoutMs: 100,
|
|
requestTimeoutMs: 100,
|
|
}),
|
|
});
|
|
try {
|
|
const result = await provider.execute(
|
|
operation === "inspect_jeb_client"
|
|
? { operation, input: {} }
|
|
: { operation, input: { count: 2, index: 0 } },
|
|
);
|
|
if (result.ok) throw new Error("Timed-out MCP request passed");
|
|
expect(result.error).toBeInstanceOf(AnalysisTimeoutError);
|
|
expect(result.error).toMatchObject({ operation, timeoutMs: 100 });
|
|
const projected = projectAnalysisError(result.error);
|
|
expect(projected.message).toContain(
|
|
stage === "catalog" ? "catalog discovery" : "tools/call",
|
|
);
|
|
expect(projected.message).toContain("100 ms");
|
|
expect(projected.remediation.action).toContain("REA_JEB_MCP_TIMEOUT_MS");
|
|
expect(projected.remediation.action).toContain("2147483647");
|
|
expect(projected.remediation.action).toContain("60000");
|
|
expect(projected.remediation.action).toContain("restart");
|
|
expect(result.error.cause).toBeDefined();
|
|
expect(result.error.cleanupIncomplete).toBe(false);
|
|
} finally {
|
|
release();
|
|
await provider.close();
|
|
await fixture.close();
|
|
}
|
|
},
|
|
);
|