@@ -64,7 +64,7 @@ async function runAgentsCli(args: string[], env?: NodeJS.ProcessEnv, stdinData?:
6464 await writeFile ( stdinPath , stdinData ?? "" , "utf8" ) ;
6565 }
6666
67- return new Promise < CliResult > ( ( resolve ) => {
67+ const runOnce = ( ) : Promise < CliResult > => new Promise < CliResult > ( ( resolve ) => {
6868 const command = [
6969 "exec" ,
7070 shellQuote ( process . execPath ) ,
@@ -99,7 +99,6 @@ async function runAgentsCli(args: string[], env?: NodeJS.ProcessEnv, stdinData?:
9999 child . stdout . on ( "data" , ( chunk : string ) => { stdout += chunk ; } ) ;
100100 child . stderr . on ( "data" , ( chunk : string ) => { stderr += chunk ; } ) ;
101101
102- // Handle process error (e.g. ENOENT, spawn failure)
103102 child . once ( "error" , ( err ) => {
104103 if ( settled ) return ;
105104 settled = true ;
@@ -111,18 +110,14 @@ async function runAgentsCli(args: string[], env?: NodeJS.ProcessEnv, stdinData?:
111110 if ( settled ) return ;
112111 settled = true ;
113112 clearTimeout ( timer ) ;
114- void rm ( stdinDir ?? "" , { recursive : true , force : true } ) ;
115113 resolve ( { code, signal, stdout, stderr } ) ;
116114 } ) ;
117115
118- // Hard timeout: kill the child and wait for close event before resolving
119116 const timer = setTimeout ( ( ) => {
120117 if ( settled ) return ;
121118 settled = true ;
122119 child . kill ( "SIGKILL" ) ;
123- // Wait for the child to actually close (or resolve after a grace period)
124120 const graceTimer = setTimeout ( ( ) => {
125- void rm ( stdinDir ?? "" , { recursive : true , force : true } ) ;
126121 resolve ( {
127122 code : null ,
128123 signal : "SIGKILL" as NodeJS . Signals ,
@@ -132,7 +127,6 @@ async function runAgentsCli(args: string[], env?: NodeJS.ProcessEnv, stdinData?:
132127 } , 3_000 ) ;
133128 child . once ( "close" , ( code , signal ) => {
134129 clearTimeout ( graceTimer ) ;
135- void rm ( stdinDir ?? "" , { recursive : true , force : true } ) ;
136130 resolve ( {
137131 code,
138132 signal : signal ?? ( "SIGKILL" as NodeJS . Signals ) ,
@@ -142,6 +136,24 @@ async function runAgentsCli(args: string[], env?: NodeJS.ProcessEnv, stdinData?:
142136 } ) ;
143137 } , CLI_TIMEOUT_MS ) ;
144138 } ) ;
139+
140+ try {
141+ let lastResult : CliResult | null = null ;
142+ for ( let attempt = 1 ; attempt <= 2 ; attempt ++ ) {
143+ const result = await runOnce ( ) ;
144+ lastResult = result ;
145+ const timedOutWithoutOutput =
146+ result . signal === "SIGKILL"
147+ && result . stdout . trim ( ) === ""
148+ && result . stderr . includes ( `[test harness] Process killed after ${ CLI_TIMEOUT_MS } ms timeout` ) ;
149+ if ( ! timedOutWithoutOutput || attempt === 2 ) {
150+ return result ;
151+ }
152+ }
153+ return lastResult ! ;
154+ } finally {
155+ await rm ( stdinDir ?? "" , { recursive : true , force : true } ) ;
156+ }
145157}
146158
147159function parseJsonStdout ( result : CliResult ) : any {
0 commit comments