@@ -2,6 +2,7 @@ import { randomUUID } from 'node:crypto';
22import {
33 accessSync ,
44 appendFileSync ,
5+ existsSync ,
56 mkdirSync ,
67 writeFileSync ,
78} from 'node:fs' ;
@@ -10,6 +11,11 @@ import { join, resolve } from 'node:path';
1011
1112const MAX_SANITIZED_LENGTH = 200 ;
1213const args = process . argv . slice ( 2 ) ;
14+ let heldInput : {
15+ uuid : string ;
16+ sessionId : string ;
17+ } | null = null ;
18+ let heldAbortPoll : ReturnType < typeof setInterval > | null = null ;
1319
1420if ( args . includes ( '--version' ) ) {
1521 console . log ( '2.1.220 (Claude Code)' ) ;
@@ -119,6 +125,20 @@ function handleInput(line: string, nativePath: string, sessionId: string): void
119125 uuid ?: string ;
120126 message ?: { role ?: string ; content ?: unknown } ;
121127 } ;
128+ if ( input . type === 'control_request' && input . request ?. subtype === 'interrupt' ) {
129+ writeOutput ( {
130+ type : 'control_response' ,
131+ response : {
132+ subtype : 'success' ,
133+ request_id : input . request_id ,
134+ response : { cancelled : [ ] , still_queued : [ ] } ,
135+ } ,
136+ } ) ;
137+ const interruptPath = process . env . CLAUDE_TEST_INTERRUPT_PATH ;
138+ if ( interruptPath ) appendFileSync ( interruptPath , 'interrupt\n' ) ;
139+ scheduleHeldAbortSettlement ( ) ;
140+ return ;
141+ }
122142 if (
123143 input . type === 'control_request'
124144 && ( input . request ?. subtype === 'initialize' || input . request ?. subtype === 'set_model' )
@@ -140,6 +160,45 @@ function handleInput(line: string, nativePath: string, sessionId: string): void
140160 const response = `echo:${ prompt } ` ;
141161 const userTimestamp = new Date ( ) . toISOString ( ) ;
142162 const assistantTimestamp = new Date ( Date . now ( ) + 1 ) . toISOString ( ) ;
163+ if ( process . env . CLAUDE_TEST_HOLD_ACTIVE === '1' ) {
164+ appendFileSync ( nativePath , `${ JSON . stringify ( {
165+ sessionId,
166+ type : 'user' ,
167+ uuid : input . uuid ,
168+ timestamp : userTimestamp ,
169+ cwd : process . cwd ( ) ,
170+ message : { role : 'user' , content : prompt } ,
171+ } ) } \n`) ;
172+ writeOutput ( {
173+ type : 'command_lifecycle' ,
174+ command_uuid : input . uuid ,
175+ state : 'queued' ,
176+ session_id : sessionId ,
177+ } ) ;
178+ writeOutput ( {
179+ type : 'system' ,
180+ subtype : 'session_state_changed' ,
181+ state : 'running' ,
182+ session_id : sessionId ,
183+ } ) ;
184+ writeOutput ( {
185+ type : 'command_lifecycle' ,
186+ command_uuid : input . uuid ,
187+ state : 'started' ,
188+ session_id : sessionId ,
189+ } ) ;
190+ writeOutput ( {
191+ type : 'user' ,
192+ uuid : input . uuid ,
193+ isReplay : true ,
194+ message : input . message ,
195+ session_id : sessionId ,
196+ } ) ;
197+ heldInput = { uuid : input . uuid , sessionId } ;
198+ const startedPath = process . env . CLAUDE_TEST_STARTED_PATH ;
199+ if ( startedPath ) writeFileSync ( startedPath , `${ input . uuid } \n` ) ;
200+ return ;
201+ }
143202 appendFileSync ( nativePath , [
144203 JSON . stringify ( {
145204 sessionId,
@@ -219,6 +278,42 @@ function handleInput(line: string, nativePath: string, sessionId: string): void
219278 } ) ;
220279}
221280
281+ function scheduleHeldAbortSettlement ( ) : void {
282+ if ( ! heldInput || heldAbortPoll ) return ;
283+ const releasePath = process . env . CLAUDE_TEST_RELEASE_PATH ;
284+ if ( ! releasePath ) return ;
285+ heldAbortPoll = setInterval ( ( ) => {
286+ if ( ! heldInput || ! existsSync ( releasePath ) ) return ;
287+ const input = heldInput ;
288+ heldInput = null ;
289+ if ( heldAbortPoll ) clearInterval ( heldAbortPoll ) ;
290+ heldAbortPoll = null ;
291+ writeOutput ( {
292+ type : 'result' ,
293+ subtype : 'error_during_execution' ,
294+ terminal_reason : 'aborted_tools' ,
295+ is_error : true ,
296+ duration_ms : 1 ,
297+ num_turns : 1 ,
298+ result : '' ,
299+ user_message_uuid : input . uuid ,
300+ session_id : input . sessionId ,
301+ } ) ;
302+ writeOutput ( {
303+ type : 'command_lifecycle' ,
304+ command_uuid : input . uuid ,
305+ state : 'cancelled' ,
306+ session_id : input . sessionId ,
307+ } ) ;
308+ writeOutput ( {
309+ type : 'system' ,
310+ subtype : 'session_state_changed' ,
311+ state : 'idle' ,
312+ session_id : input . sessionId ,
313+ } ) ;
314+ } , 5 ) ;
315+ }
316+
222317function messageText ( content : unknown ) : string {
223318 if ( typeof content === 'string' ) return content ;
224319 if ( ! Array . isArray ( content ) ) return '' ;
0 commit comments