@@ -161,6 +161,9 @@ export class Task extends EventEmitter<TaskEvents> implements TaskLike {
161161
162162 todoList ?: TodoItem [ ]
163163
164+ private readonly timeoutMap = new Map < number , NodeJS . Timeout > ( )
165+ private nextTimeoutId = 0
166+
164167 readonly rootTask : Task | undefined = undefined
165168 readonly parentTask : Task | undefined = undefined
166169 readonly taskNumber : number
@@ -855,8 +858,6 @@ export class Task extends EventEmitter<TaskEvents> implements TaskLike {
855858 await this . addToClineMessages ( { ts : askTs , type : "ask" , ask : type , text, isProtected } )
856859 }
857860
858- let timeouts : NodeJS . Timeout [ ] = [ ]
859-
860861 // Automatically approve if the ask according to the user's settings.
861862 const provider = this . providerRef . deref ( )
862863 const state = provider ? await provider . getState ( ) : undefined
@@ -867,12 +868,22 @@ export class Task extends EventEmitter<TaskEvents> implements TaskLike {
867868 } else if ( approval . decision === "deny" ) {
868869 this . denyAsk ( )
869870 } else if ( approval . decision === "timeout" ) {
870- timeouts . push (
871- setTimeout ( ( ) => {
872- const { askResponse, text, images } = approval . fn ( )
873- this . handleWebviewAskResponse ( askResponse , text , images )
874- } , approval . timeout ) ,
875- )
871+ const timeoutId = this . nextTimeoutId ++
872+
873+ const timer = setTimeout ( ( ) => {
874+ const { askResponse, text, images } = approval . fn ( )
875+ this . handleWebviewAskResponse ( askResponse , text , images )
876+ this . timeoutMap . delete ( timeoutId )
877+ } , approval . timeout )
878+
879+ this . timeoutMap . set ( timeoutId , timer )
880+
881+ if ( approval . askType === "followup" ) {
882+ provider ?. postMessageToWebview ( {
883+ type : "zgsmFollowupClearTimeout" ,
884+ value : timeoutId ,
885+ } )
886+ }
876887 }
877888
878889 // The state is mutable if the message is complete and the task will
@@ -891,47 +902,53 @@ export class Task extends EventEmitter<TaskEvents> implements TaskLike {
891902 const statusMutationTimeout = 2_000
892903
893904 if ( isInteractiveAsk ( type ) ) {
894- timeouts . push (
895- setTimeout ( ( ) => {
896- const message = this . findMessageByTimestamp ( askTs )
905+ const timeoutId = this . nextTimeoutId ++
906+ const timer = setTimeout ( ( ) => {
907+ const message = this . findMessageByTimestamp ( askTs )
908+
909+ if ( message ) {
910+ this . interactiveAsk = message
911+ this . emit ( RooCodeEventName . TaskInteractive , this . taskId )
912+ provider ?. postMessageToWebview ( { type : "interactionRequired" } )
913+ }
914+ this . timeoutMap . delete ( timeoutId )
915+ } , statusMutationTimeout )
897916
898- if ( message ) {
899- this . interactiveAsk = message
900- this . emit ( RooCodeEventName . TaskInteractive , this . taskId )
901- provider ?. postMessageToWebview ( { type : "interactionRequired" } )
902- }
903- } , statusMutationTimeout ) ,
904- )
917+ this . timeoutMap . set ( timeoutId , timer )
905918 } else if ( isResumableAsk ( type ) ) {
906- timeouts . push (
907- setTimeout ( ( ) => {
908- const message = this . findMessageByTimestamp ( askTs )
919+ const timeoutId = this . nextTimeoutId ++
920+ const timer = setTimeout ( ( ) => {
921+ const message = this . findMessageByTimestamp ( askTs )
909922
910- if ( message ) {
911- this . resumableAsk = message
912- this . emit ( RooCodeEventName . TaskResumable , this . taskId )
913- }
914- } , statusMutationTimeout ) ,
915- )
923+ if ( message ) {
924+ this . resumableAsk = message
925+ this . emit ( RooCodeEventName . TaskResumable , this . taskId )
926+ }
927+ this . timeoutMap . delete ( timeoutId )
928+ } , statusMutationTimeout )
929+
930+ this . timeoutMap . set ( timeoutId , timer )
916931 } else if ( isIdleAsk ( type ) ) {
917- timeouts . push (
918- setTimeout ( ( ) => {
919- const message = this . findMessageByTimestamp ( askTs )
932+ const timeoutId = this . nextTimeoutId ++
933+ const timer = setTimeout ( ( ) => {
934+ const message = this . findMessageByTimestamp ( askTs )
920935
921- if ( message ) {
922- this . idleAsk = message
923- this . emit ( RooCodeEventName . TaskIdle , this . taskId )
924- }
925- } , statusMutationTimeout ) ,
926- )
936+ if ( message ) {
937+ this . idleAsk = message
938+ this . emit ( RooCodeEventName . TaskIdle , this . taskId )
939+ }
940+ this . timeoutMap . delete ( timeoutId )
941+ } , statusMutationTimeout )
942+
943+ this . timeoutMap . set ( timeoutId , timer )
927944 }
928945 } else if ( isMessageQueued ) {
929946 console . log ( `Task#ask: will process message queue -> type: ${ type } ` )
930947
931948 const message = this . messageQueueService . dequeueMessage ( )
932949
933950 if ( message ) {
934- // Check if this is a tool approval ask that needs to be handled.
951+ // Check if this is a tool approval ask Pthat needs to be handled.
935952 if (
936953 type === "tool" ||
937954 type === "command" ||
@@ -971,7 +988,7 @@ export class Task extends EventEmitter<TaskEvents> implements TaskLike {
971988 this . askResponseImages = undefined
972989
973990 // Cancel the timeouts if they are still running.
974- timeouts . forEach ( ( timeout ) => clearTimeout ( timeout ) )
991+ this . clearAllAutoApprovalTimeouts ( )
975992
976993 // Switch back to an active state.
977994 if ( this . idleAsk || this . resumableAsk || this . interactiveAsk ) {
@@ -985,6 +1002,23 @@ export class Task extends EventEmitter<TaskEvents> implements TaskLike {
9851002 return result
9861003 }
9871004
1005+ public clearAutoApprovalTimeout ( timeoutId : number ) : boolean {
1006+ const timer = this . timeoutMap . get ( timeoutId )
1007+ if ( timer ) {
1008+ clearTimeout ( timer )
1009+ this . timeoutMap . delete ( timeoutId )
1010+ return true
1011+ }
1012+ return false
1013+ }
1014+
1015+ public clearAllAutoApprovalTimeouts ( ) : void {
1016+ for ( const [ timeoutId , timer ] of this . timeoutMap ) {
1017+ clearTimeout ( timer )
1018+ }
1019+ this . timeoutMap . clear ( )
1020+ }
1021+
9881022 public setMessageResponse ( text : string , images ?: string [ ] ) {
9891023 this . handleWebviewAskResponse ( "messageResponse" , text , images )
9901024 }
0 commit comments