|
9 | 9 | onAgentEvent, |
10 | 10 | queueAgentHarnessMessage, |
11 | 11 | resetAgentEventsForTest, |
12 | | - wrapToolWithBeforeToolCallHook, |
13 | 12 | type AgentEventPayload, |
14 | 13 | type EmbeddedRunAttemptParams, |
15 | 14 | } from "openclaw/plugin-sdk/agent-harness-runtime"; |
@@ -3366,112 +3365,96 @@ describe("runCodexAppServerAttempt", () => { |
3366 | 3365 | }); |
3367 | 3366 |
|
3368 | 3367 | it("emits request-boundary terminal diagnostics when a wrapped dynamic tool does not", async () => { |
3369 | | - const harness = createStartedThreadHarness(); |
3370 | 3368 | const diagnosticEvents: DiagnosticEventPayload[] = []; |
3371 | 3369 | const unsubscribeDiagnostics = onInternalDiagnosticEvent((event) => |
3372 | 3370 | diagnosticEvents.push(event), |
3373 | 3371 | ); |
3374 | | - const rawTool = { |
3375 | | - name: "echo", |
3376 | | - description: "echo test tool", |
3377 | | - parameters: { |
3378 | | - type: "object", |
3379 | | - properties: {}, |
3380 | | - additionalProperties: false, |
3381 | | - }, |
3382 | | - execute: vi.fn(async () => ({ |
3383 | | - content: [{ type: "text" as const, text: "echo done" }], |
3384 | | - details: {}, |
3385 | | - })), |
3386 | | - }; |
3387 | | - rawTool.execute.mockImplementationOnce(async () => { |
3388 | | - emitTrustedDiagnosticEvent({ |
3389 | | - type: "tool.execution.completed", |
3390 | | - runId: "other-run", |
3391 | | - sessionId: "session-1", |
3392 | | - sessionKey: "agent:main:session-1", |
3393 | | - toolName: "echo", |
3394 | | - toolCallId: "call-echo-unobserved-terminal", |
3395 | | - durationMs: 1, |
3396 | | - }); |
3397 | | - return { |
3398 | | - content: [{ type: "text" as const, text: "echo done" }], |
3399 | | - details: {}, |
3400 | | - }; |
3401 | | - }); |
3402 | | - const markedWrappedTool = { |
3403 | | - ...wrapToolWithBeforeToolCallHook(rawTool as never), |
3404 | | - execute: rawTool.execute, |
3405 | | - }; |
3406 | | - testing.setOpenClawCodingToolsFactoryForTests(() => [markedWrappedTool as never]); |
3407 | | - |
3408 | | - const params = createParams( |
3409 | | - path.join(tempDir, "session.jsonl"), |
3410 | | - path.join(tempDir, "workspace"), |
3411 | | - ); |
3412 | | - params.disableTools = false; |
3413 | | - params.runtimePlan = createCodexRuntimePlanFixture(); |
3414 | | - |
3415 | | - const run = runCodexAppServerAttempt(params); |
3416 | | - await harness.waitForMethod("thread/start"); |
3417 | | - |
3418 | | - const toolResult = (await harness.handleServerRequest({ |
3419 | | - id: "request-echo-unobserved-terminal-tool", |
3420 | | - method: "item/tool/call", |
3421 | | - params: { |
| 3372 | + try { |
| 3373 | + const call = { |
3422 | 3374 | threadId: "thread-1", |
3423 | 3375 | turnId: "turn-1", |
3424 | 3376 | callId: "call-echo-unobserved-terminal", |
3425 | 3377 | namespace: null, |
3426 | 3378 | tool: "echo", |
3427 | 3379 | arguments: {}, |
3428 | | - }, |
3429 | | - })) as { |
3430 | | - contentItems?: Array<{ text?: string; type?: string }>; |
3431 | | - success?: boolean; |
3432 | | - }; |
3433 | | - expect(toolResult.success).toBe(true); |
3434 | | - |
3435 | | - await harness.completeTurn({ threadId: "thread-1", turnId: "turn-1" }); |
3436 | | - await run; |
3437 | | - await flushDiagnosticEvents(); |
3438 | | - unsubscribeDiagnostics(); |
| 3380 | + } satisfies CodexDynamicToolCallParams; |
3439 | 3381 |
|
3440 | | - const toolDiagnosticEvents = diagnosticEvents.filter( |
3441 | | - ( |
3442 | | - event, |
3443 | | - ): event is Extract< |
3444 | | - DiagnosticEventPayload, |
3445 | | - { type: "tool.execution.started" | "tool.execution.completed" | "tool.execution.error" } |
3446 | | - > => event.type.startsWith("tool.execution."), |
3447 | | - ); |
3448 | | - expect( |
3449 | | - toolDiagnosticEvents.map((event) => ({ |
3450 | | - runId: event.runId, |
3451 | | - type: event.type, |
3452 | | - toolName: event.toolName, |
3453 | | - toolCallId: event.toolCallId, |
3454 | | - })), |
3455 | | - ).toEqual([ |
3456 | | - { |
| 3382 | + emitDynamicToolStartedDiagnostic({ |
| 3383 | + call, |
3457 | 3384 | runId: "run-1", |
3458 | | - type: "tool.execution.started", |
3459 | | - toolName: "echo", |
3460 | | - toolCallId: "call-echo-unobserved-terminal", |
3461 | | - }, |
3462 | | - { |
3463 | | - runId: "other-run", |
| 3385 | + sessionId: "session-1", |
| 3386 | + sessionKey: "agent:main:session-1", |
| 3387 | + }); |
| 3388 | + emitTrustedDiagnosticEvent({ |
3464 | 3389 | type: "tool.execution.completed", |
| 3390 | + runId: "other-run", |
| 3391 | + sessionId: "session-1", |
| 3392 | + sessionKey: "agent:main:session-1", |
3465 | 3393 | toolName: "echo", |
3466 | 3394 | toolCallId: "call-echo-unobserved-terminal", |
3467 | | - }, |
3468 | | - { |
| 3395 | + durationMs: 1, |
| 3396 | + }); |
| 3397 | + expect( |
| 3398 | + testing.hasPendingDynamicToolTerminalDiagnostic({ |
| 3399 | + call, |
| 3400 | + runId: "run-1", |
| 3401 | + sessionId: "session-1", |
| 3402 | + sessionKey: "agent:main:session-1", |
| 3403 | + }), |
| 3404 | + ).toBe(false); |
| 3405 | + |
| 3406 | + emitDynamicToolTerminalDiagnostic({ |
| 3407 | + call, |
3469 | 3408 | runId: "run-1", |
3470 | | - type: "tool.execution.completed", |
3471 | | - toolName: "echo", |
3472 | | - toolCallId: "call-echo-unobserved-terminal", |
3473 | | - }, |
3474 | | - ]); |
| 3409 | + sessionId: "session-1", |
| 3410 | + sessionKey: "agent:main:session-1", |
| 3411 | + durationMs: 1, |
| 3412 | + response: { |
| 3413 | + success: true, |
| 3414 | + contentItems: [{ type: "inputText", text: "echo done" }], |
| 3415 | + }, |
| 3416 | + }); |
| 3417 | + |
| 3418 | + await flushDiagnosticEvents(); |
| 3419 | + |
| 3420 | + const toolDiagnosticEvents = diagnosticEvents.filter( |
| 3421 | + ( |
| 3422 | + event, |
| 3423 | + ): event is Extract< |
| 3424 | + DiagnosticEventPayload, |
| 3425 | + { type: "tool.execution.started" | "tool.execution.completed" | "tool.execution.error" } |
| 3426 | + > => event.type.startsWith("tool.execution."), |
| 3427 | + ); |
| 3428 | + expect( |
| 3429 | + toolDiagnosticEvents.map((event) => ({ |
| 3430 | + runId: event.runId, |
| 3431 | + type: event.type, |
| 3432 | + toolName: event.toolName, |
| 3433 | + toolCallId: event.toolCallId, |
| 3434 | + })), |
| 3435 | + ).toEqual([ |
| 3436 | + { |
| 3437 | + runId: "run-1", |
| 3438 | + type: "tool.execution.started", |
| 3439 | + toolName: "echo", |
| 3440 | + toolCallId: "call-echo-unobserved-terminal", |
| 3441 | + }, |
| 3442 | + { |
| 3443 | + runId: "other-run", |
| 3444 | + type: "tool.execution.completed", |
| 3445 | + toolName: "echo", |
| 3446 | + toolCallId: "call-echo-unobserved-terminal", |
| 3447 | + }, |
| 3448 | + { |
| 3449 | + runId: "run-1", |
| 3450 | + type: "tool.execution.completed", |
| 3451 | + toolName: "echo", |
| 3452 | + toolCallId: "call-echo-unobserved-terminal", |
| 3453 | + }, |
| 3454 | + ]); |
| 3455 | + } finally { |
| 3456 | + unsubscribeDiagnostics(); |
| 3457 | + } |
3475 | 3458 | }); |
3476 | 3459 |
|
3477 | 3460 | it("does not duplicate terminal diagnostics for wrapped dynamic tool blocks", async () => { |
|
0 commit comments