test(tools): verify timeout abort prevents post-timeout side effects
This commit is contained in:
@@ -59,6 +59,31 @@ const cancellableTool: Tool = {
|
||||
},
|
||||
};
|
||||
|
||||
function createSideEffectTool(sideEffect: { fired: boolean }): Tool {
|
||||
return {
|
||||
name: 'test.side_effect',
|
||||
description: 'Cancellable side effect',
|
||||
inputSchema: { type: 'object', properties: {} },
|
||||
execute: async (_args, context) => {
|
||||
return await new Promise((resolve) => {
|
||||
const timer = setTimeout(() => {
|
||||
sideEffect.fired = true;
|
||||
resolve({ success: true, output: 'side effect fired' });
|
||||
}, 120);
|
||||
const onAbort = () => {
|
||||
clearTimeout(timer);
|
||||
resolve({ success: false, output: '', error: 'aborted' });
|
||||
};
|
||||
if (context?.signal?.aborted) {
|
||||
onAbort();
|
||||
return;
|
||||
}
|
||||
context?.signal?.addEventListener('abort', onAbort, { once: true });
|
||||
});
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
describe('ToolExecutor', () => {
|
||||
it('executes a tool and returns result', async () => {
|
||||
const registry = new ToolRegistry();
|
||||
@@ -114,6 +139,21 @@ describe('ToolExecutor', () => {
|
||||
expect(result.error).toContain('timed out');
|
||||
});
|
||||
|
||||
it('prevents post-timeout side effects for cancellable tools', async () => {
|
||||
const sideEffect = { fired: false };
|
||||
const registry = new ToolRegistry();
|
||||
registry.register(createSideEffectTool(sideEffect));
|
||||
const hooks = new HookEngine({ confirm: [], log: [], silent: [] });
|
||||
const executor = new ToolExecutor(registry, hooks, { defaultTimeoutMs: 30 });
|
||||
|
||||
const result = await executor.execute('test.side_effect', {});
|
||||
expect(result.success).toBe(false);
|
||||
expect(result.error).toContain('timed out');
|
||||
|
||||
await new Promise(resolve => setTimeout(resolve, 180));
|
||||
expect(sideEffect.fired).toBe(false);
|
||||
});
|
||||
|
||||
it('truncates large output', async () => {
|
||||
const registry = new ToolRegistry();
|
||||
registry.register(bigOutputTool);
|
||||
|
||||
Reference in New Issue
Block a user