@@ -101,16 +101,28 @@ function runHookCommand(command, input = {}, env = {}, timeoutMs = 10000) {
101101 return new Promise ( ( resolve , reject ) => {
102102 const isWindows = process . platform === 'win32' ;
103103 const mergedEnv = { ...process . env , CLAUDE_PLUGIN_ROOT : REPO_ROOT , ...env } ;
104- const resolvedCommand = isWindows
105- ? command . replace ( / \$ \{ ( [ A - Z _ ] [ A - Z 0 - 9 _ ] * ) \} / g, ( _ , name ) => String ( mergedEnv [ name ] || '' ) )
106- : command ;
104+ const resolvedCommand = command . replace (
105+ / \$ \{ ( [ A - Z _ ] [ A - Z 0 - 9 _ ] * ) \} / g,
106+ ( _ , name ) => String ( mergedEnv [ name ] || '' )
107+ ) ;
108+
109+ const nodeMatch = resolvedCommand . match ( / ^ n o d e \s + " ( [ ^ " ] + ) " \s * ( .* ) $ / ) ;
110+ const useDirectNodeSpawn = Boolean ( nodeMatch ) ;
107111 const shell = isWindows ? 'cmd' : 'bash' ;
108112 const shellArgs = isWindows ? [ '/d' , '/s' , '/c' , resolvedCommand ] : [ '-lc' , resolvedCommand ] ;
109-
110- const proc = spawn ( shell , shellArgs , {
111- env : mergedEnv ,
112- stdio : [ 'pipe' , 'pipe' , 'pipe' ]
113- } ) ;
113+ const nodeArgs = nodeMatch
114+ ? [
115+ nodeMatch [ 1 ] ,
116+ ...Array . from (
117+ nodeMatch [ 2 ] . matchAll ( / " ( [ ^ " ] * ) " | ( \S + ) / g) ,
118+ m => m [ 1 ] !== undefined ? m [ 1 ] : m [ 2 ]
119+ )
120+ ]
121+ : [ ] ;
122+
123+ const proc = useDirectNodeSpawn
124+ ? spawn ( 'node' , nodeArgs , { env : mergedEnv , stdio : [ 'pipe' , 'pipe' , 'pipe' ] } )
125+ : spawn ( shell , shellArgs , { env : mergedEnv , stdio : [ 'pipe' , 'pipe' , 'pipe' ] } ) ;
114126
115127 let stdout = '' ;
116128 let stderr = '' ;
0 commit comments