test: add focused seams for faster isolated tests

This commit is contained in:
Peter Steinberger
2026-05-06 00:52:21 +01:00
parent 46c99cff0b
commit e428a2dfe2
9 changed files with 95 additions and 54 deletions

View File

@@ -369,6 +369,7 @@ describe("runCodexAppServerAttempt", () => {
afterEach(async () => {
__testing.resetCodexAppServerClientFactoryForTests();
__testing.resetOpenClawCodingToolsFactoryForTests();
resetCodexRateLimitCacheForTests();
nativeHookRelayTesting.clearNativeHookRelaysForTests();
resetAgentEventsForTest();
@@ -475,6 +476,18 @@ describe("runCodexAppServerAttempt", () => {
params.config = { tools: { profile: "coding" } };
params.sourceReplyDeliveryMode = "message_tool_only";
params.messageProvider = "whatsapp";
let seenForceMessageTool: boolean | undefined;
__testing.setOpenClawCodingToolsFactoryForTests((options) => {
seenForceMessageTool = options?.forceMessageTool;
return [
{
name: "message",
description: "message test tool",
parameters: { type: "object", properties: {} },
execute: vi.fn(),
},
] as never;
});
const dynamicTools = await __testing.buildDynamicTools({
params,
@@ -489,6 +502,7 @@ describe("runCodexAppServerAttempt", () => {
});
const dynamicToolNames = dynamicTools.map((tool) => tool.name);
expect(seenForceMessageTool).toBe(true);
expect(dynamicToolNames).toContain("message");
});
@@ -517,6 +531,18 @@ describe("runCodexAppServerAttempt", () => {
},
}),
);
let seenRunSessionKey: string | undefined;
__testing.setOpenClawCodingToolsFactoryForTests((options) => {
seenRunSessionKey = options?.runSessionKey;
return [
{
name: "session_status",
description: "session status test tool",
parameters: { type: "object", properties: {} },
execute: vi.fn(async () => ({ details: { sessionKey: options?.runSessionKey } })),
},
] as never;
});
const dynamicTools = await __testing.buildDynamicTools({
params,
@@ -533,6 +559,7 @@ describe("runCodexAppServerAttempt", () => {
expect(sessionStatus).toBeDefined();
const result = await sessionStatus?.execute("call-current", { sessionKey: "current" });
expect(seenRunSessionKey).toBe("agent:main:main");
expect((result?.details as { sessionKey?: string } | undefined)?.sessionKey).toBe(
"agent:main:main",
);

View File

@@ -1,3 +1,4 @@
import { AsyncLocalStorage } from "node:async_hooks";
import { createHash } from "node:crypto";
import fs from "node:fs/promises";
import path from "node:path";
@@ -46,8 +47,8 @@ import {
resolveCodexAppServerAuthProfileIdForAgent,
} from "./auth-bridge.js";
import {
createCodexAppServerClientFactoryTestHooks,
defaultCodexAppServerClientFactory,
type CodexAppServerClientFactory,
} from "./client-factory.js";
import {
isCodexAppServerApprovalRequest,
@@ -126,8 +127,16 @@ const CODEX_BOOTSTRAP_CONTEXT_ORDER = new Map<string, number>([
type OpenClawCodingToolsOptions = NonNullable<
Parameters<(typeof import("openclaw/plugin-sdk/agent-harness"))["createOpenClawCodingTools"]>[0]
>;
type OpenClawCodingToolsFactory =
(typeof import("openclaw/plugin-sdk/agent-harness"))["createOpenClawCodingTools"];
let clientFactory = defaultCodexAppServerClientFactory;
const testClientFactoryStorage = new AsyncLocalStorage<CodexAppServerClientFactory | undefined>();
const clientFactory = defaultCodexAppServerClientFactory;
let openClawCodingToolsFactoryForTests: OpenClawCodingToolsFactory | undefined;
function resolveCodexAppServerClientFactory(): CodexAppServerClientFactory {
return testClientFactoryStorage.getStore() ?? clientFactory;
}
function emitCodexAppServerEvent(
params: EmbeddedRunAttemptParams,
@@ -351,7 +360,7 @@ export async function runCodexAppServerAttempt(
} = {},
): Promise<EmbeddedRunAttemptResult> {
const attemptStartedAt = Date.now();
const attemptClientFactory = clientFactory;
const attemptClientFactory = resolveCodexAppServerClientFactory();
const pluginConfig = readCodexPluginConfig(options.pluginConfig);
const appServer = resolveCodexAppServerRuntimeOptions({ pluginConfig });
const resolvedWorkspace = resolveUserPath(params.workspaceDir);
@@ -1478,7 +1487,9 @@ async function buildDynamicTools(input: DynamicToolBuildParams) {
}
const modelHasVision = params.model.input?.includes("image") ?? false;
const agentDir = params.agentDir ?? resolveAgentDir(params.config ?? {}, input.sessionAgentId);
const { createOpenClawCodingTools } = await import("openclaw/plugin-sdk/agent-harness");
const createOpenClawCodingTools =
openClawCodingToolsFactoryForTests ??
(await import("openclaw/plugin-sdk/agent-harness")).createOpenClawCodingTools;
const allTools = createOpenClawCodingTools({
agentId: input.sessionAgentId,
...buildEmbeddedAttemptToolRunContext(params),
@@ -1963,7 +1974,16 @@ export const __testing = {
buildDynamicTools,
filterToolsForVisionInputs,
handleDynamicToolCallWithTimeout,
...createCodexAppServerClientFactoryTestHooks((factory) => {
clientFactory = factory;
}),
setOpenClawCodingToolsFactoryForTests(factory: OpenClawCodingToolsFactory): void {
openClawCodingToolsFactoryForTests = factory;
},
resetOpenClawCodingToolsFactoryForTests(): void {
openClawCodingToolsFactoryForTests = undefined;
},
setCodexAppServerClientFactoryForTests(factory: CodexAppServerClientFactory): void {
testClientFactoryStorage.enterWith(factory);
},
resetCodexAppServerClientFactoryForTests(): void {
testClientFactoryStorage.enterWith(undefined);
},
} as const;