nodejs / help

:sparkles: Need help with Node.js? File an Issue here. :rocket:
1.46k stars 279 forks source link

killing multiple child processes #4050

Open CoyiCodes opened 1 year ago

CoyiCodes commented 1 year ago

Details

Hi I am trying to kill a process but I can not do it. I created a flask server with python and packed it with pyinstaller. When I start my electron app I start the process like this ( and it starts ok):

This is used under app.on('ready'...)

const { execFile, spawn } = require('child_process');
var kill = require('tree-kill');
let child;

function startExecutable() {
    let browseDirectory = process.cwd() + "/api/Tracker.exe"
    child = execFile(browseDirectory)
}

This creates 2 processes:

Task manager view

I am trying to kill the process on app.on('window-all-closed'...)

function stopExecutable() {
    // console.log(child.pid)
    // child.kill('SIGKILL')
    // kill(child.pid, 'SIGTERM');
    kill(child.pid, 'SIGKILL');
}

But this only kills PID 8868 and other one keeps running.

But When I run code the code below on command prompt. It kills all of them

taskkill /F /IM Tracker.exe /T

They all kill only one of the processes. How Do I kill all processes with the same name?

Node.js version

v16.13.1

Example code

No response

Operating system

Windows 10

Scope

code

Module and version

Not applicable.

krrishdholakia commented 1 year ago

@CoyiCodes Are you running the code with elevated privileges? - Clerkie

CoyiCodes commented 1 year ago

elevated privileges

I am packing it with electron-builder then I tried both starting it by duble clicking and runing it as admin. Nothing changed unfortunately.

xinzhao111 commented 1 year ago

I also encountered the same problem!I'm so sad

preveen-stack commented 1 year ago

cc @nodejs/child_process PTAL

hoboly commented 11 months ago

taskkill /F /PID xxxx /T can solve the problem

morningf commented 6 months ago

This is the behavior of PyInstaller, see https://pyinstaller.readthedocs.io/en/stable/advanced-topics.html#the-bootstrap-process-in-detail.

lizhongyue248 commented 4 months ago

This is the behavior of PyInstaller, see https://pyinstaller.readthedocs.io/en/stable/advanced-topics.html#the-bootstrap-process-in-detail.

You are correct. Do you have any good solutions? At present, I can only kill all associated processes through tree-kill, but I don't think this is the best solution.

fedehann commented 4 months ago

You are correct. Do you have any good solutions? At present, I can only kill all associated processes through tree-kill, but I don't think this is the best solution.

I'm unable to solve the issue even by killing all the associated processes. I tried the following thing:

var kill = require('tree-kill');
let mainProcessPid
...

app.on("ready", () => {
    createWindow();
    mainProcessPid = mainWindow.webContents.getOSProcessId()
})

...

app.on("window-all-closed", () => {
    if(process.platform !== "darwin") {
        // Retrieve main process Pid
        // Kill main process and all the subprocesses
        kill(mainProcessPid)
        // Quit
        app.quit()
    }
})
morningf commented 4 months ago

This is the behavior of PyInstaller, see https://pyinstaller.readthedocs.io/en/stable/advanced-topics.html#the-bootstrap-process-in-detail.

You are correct. Do you have any good solutions? At present, I can only kill all associated processes through tree-kill, but I don't think this is the best solution.

Currently, I'm using the following approach:

  1. When starting a Python process, you can obtain its PID.
  2. Find another process with the same name but different PIDs.
  3. If step 2 finds one, kill this process and automatically terminate it when getting directly obtained by another progress at that time.
  4. If step 2 doesn't find any, then directly kill the process corresponding to the given PID.
RedYetiDev commented 1 month ago

Hi! Node.js (AFAIK) doesn't support killing processes by name. If you manage to obtain the PID of the processes to kill, you can do it like that.

Additionally, via the command you provided, taskkill /F /IM Tracker.exe /T, you can kill processes via child_process.

Do you need more help, or can this be closed?

Cosmicoppai commented 1 month ago

That's what I found best, also suggested by others, fairly simple in use and less error prone

function killPythonServer() {
    const killCmd = `tskill processName`;
    spawn('cmd.exe', ['/c', killCmd]);
}

app.on('quit', (event) => {
    killPythonServer();
});
lizhongyue248 commented 1 month ago

That's what I found best, also suggested by others, fairly simple in use and less error prone

function killPythonServer() {
    const killCmd = `tskill processName`;
    spawn('cmd.exe', ['/c', killCmd]);
}

app.on('quit', (event) => {
    killPythonServer();
});

But this method only works on Windows...

Cosmicoppai commented 1 month ago
function killPythonServer() {
    const killCmd = `tskill processName`;
    spawn('cmd.exe', ['/c', killCmd]);
}

app.on('quit', (event) => {
    killPythonServer();
});

@lizhongyue248 yeah, I meant we can use the general idea of killing using the process name. Similar action in unix can be achieve via pkill -f processName

cosmicoppai@CosmicOppai:~$ ps -aux | grep 'LiSA'
cosmico+    1353  5.4  0.7 325836 60480 pts/0    Sl+  07:20   0:00 python3 LiSA.py
cosmico+    1359  0.1  0.5 225672 41256 pts/0    Sl+  07:20   0:00 python3 LiSA.py
cosmico+    1364  0.0  0.5 225672 40988 pts/0    Sl+  07:20   0:00 python3 LiSA.py
cosmico+    1370  0.0  0.5 225672 40960 pts/0    Sl+  07:20   0:00 python3 LiSA.py
cosmico+    1377  0.0  0.5 225672 40904 pts/0    Sl+  07:20   0:00 python3 LiSA.py
cosmico+    1748  0.0  0.0   4032  2036 pts/2    S+   07:20   0:00 grep --color=auto LiSA
cosmicoppai@CosmicOppai:~$ pkill -f LiSA
cosmicoppai@CosmicOppai:~$ ps -aux | grep 'LiSA'
cosmico+    1802  0.0  0.0   4032  2020 pts/2    S+   07:20   0:00 grep --color=auto LiSA
cosmicoppai@CosmicOppai:~$