Why can I not kill my child process in nodejs on windows?
Asked Answered
S

6

28
exec = require('child_process').exec;

child = exec('node child.js');
child.stdout.pipe(process.stdout);
child.kill('SIGKILL');

function wait() {
    setTimeout(wait, 1000);
    child.kill('SIGKILL');
}
wait();

The above code does not work. The child starts and will continue to write output indefinitely. I can not figure out how to kill this child process. I am running node v0.11.9 in Windows 7. I know that Windows does not use POSIX signals but sending it 'WM_QUIT' results in an exception. Is my best solution to setup an event protocol on stdin?

Sena answered 16/5, 2014 at 23:38 Comment(3)
Node actually emulates SIGKILL in Windows I believe. So theoretically the code should work fine.Mcabee
And yet it doesn't.Sena
It works on my mac it seems, I think it is not emulating the send signal correctly on windows.Sena
T
56

This still doesn't work for me with the current accepted answer. A work around on windows you can use is to call upon the windows taskkill program to kill the child process for you. Not quite as nice but it works. When you spawn the child you get a ProcessID (pid) stored in the child object returned when spawning, you can use with taskkill to kill the process.

var spawn = require('child_process').spawn;    
spawn("taskkill", ["/pid", child.pid, '/f', '/t']);
Tadio answered 27/1, 2015 at 5:37 Comment(1)
THANK YOU! I spent literally the whole day trying to figure out how to kill off a process and this was the only thing that worked. I tried literally every other option. Thank you so much!Valence
S
10

I had to use the following package to kill my child process:

https://www.npmjs.com/package/tree-kill

The regular .kill command wouldn't work for me either on a raspberry pi.

Solicitude answered 16/12, 2015 at 21:56 Comment(4)
This works great with shelljs, for example:Brno
const kill = require('tree-kill');Brno
let process = shell.exec("some command running in the background", {async:true});Brno
kill(process.pid);Brno
P
7

If you want to be able to kill child processes via SIGKILL, use spawn instead, as spawn will create a child process (instead of a new shell like exec:

var exec = require('child_process').spawn;

Alternatively, you could pass the timeout parameter to exec, which will kill the process after that many milliseconds.

child = exec('node child.js', { timeout: 1000 });
Peduncle answered 16/5, 2014 at 23:54 Comment(5)
How is this related? exec is built on spawn and both return instance of ChildProcess, which means child.kill function is same for both.Mcabee
This works. I am still a little unsure how exec is different than spawn if unlike the C exec, it does not overlay the parent process memory. The fact that the exec child continues to run asynchronously along side its parent yet cannot receive signal input like a spawned process is to me a mystery. Maybe exec.kill should be undefined or throw the exception "if you want to send signals use spawn". Please explain to me the internals of node exec vs spawn.Sena
@NickSotiros Updated answer. Please upvote and accept if it answers your question.Peduncle
On my mac running with exec and not spawn works fine, but not on windows. However I now have another problem, I want to exec "coffee --nodejs --harmony_generators child.coffee" and it seems that the coffee is forking another node child which then becomes a zombie. So I'm back at square one. Why is it so hard to just run something in the background and kill it when you want to?Sena
I tested SIGKILL in windows 8.1, on node 0.10.25, and it works.Ocular
L
5

Just an update

Now this code works (tested with Node.js 8.9.3 and Windows 10):

spawn = require('child_process').spawn;
child = spawn('node', ['child.js']);

setTimeout(function() {
    child.kill();
    }, 5000
);
Landaulet answered 21/8, 2018 at 12:52 Comment(5)
child.kill exists since v0.1.90. This should be the answer.Craft
OK, then could you vote the answer please? thank you @DushyantBangalLandaulet
I believe this works because Node acts on the received signal but Windows based programs usually don't. In my experience spawned Windows' processes receive exit but do not close.Jesuitism
this isn't always working, for some reason, even if i run it 3 times: vpnProcess.kill(); vpnProcess.kill('SIGTERM'); vpnProcess.kill('SIGKILL');, it still doesn't kill the process.Ephemera
This works only because this code is not using the shell. The code in the question is not.Eweneck
I
2

There is no problem under macOS. Under Windows, kill only exits the process and cannot close it. Under Windows, you need to manually destroy it.

const cp = require('child_process').spawn('your code')

// add this code
cp.stdout.destroy()
cp.stdin.destroy()
cp.stderr.destroy()
cp.kill()
Infantile answered 4/11, 2023 at 7:35 Comment(0)
C
0

check this code it worked for me.


    var killer = require('child_process');

    killer=exec('taskkill /F /pid '+child.pid);


Here killer is a variable and child is your child process. when you create a child process it has many attributes associated with it and pid is one of them. for more details on child process attributes and function check this node.js child process.

This program is to kill child process in windows environment.

Clasp answered 1/11, 2015 at 18:15 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.