【发布时间】:2016-01-04 22:00:40
【问题描述】:
不是this的重复:我可以很好地杀死进程,我想知道如何在进程中检测到它被杀死并正常关闭。
概述:
我有一个 CLI 工具来生成和终止子 node.js 进程。演示代码包含在这三个文件中:
spawn.js -- 将生成 child.js 脚本,分离。为简单起见,我将孩子的 stdio 通过管道传输到 out.log 文件
child.js -- 一个写入文件的简单计数器,使用readline 方法在 Windows 中检测模拟的 SIGINT
kill.js -- 在子进程上调用process.kill(),使用它的PID
代码:
spawn.js
'use strict';
var spawn = require('child_process').spawn;
var fs = require('fs');
var path = require('path');
var childFilePath = path.resolve(__dirname, 'child.js');
var out = fs.openSync('./out.log', 'a');
var err = fs.openSync('./out.log', 'a');
var options = {
detached: true,
stdio: ['ignore', out, err],
};
var child = spawn(process.execPath, [childFilePath], options);
child.unref();
child.js
'use strict';
var fs = require('fs');
var path = require('path');
if (process.platform === 'win32') {
console.log('win32 true');
var rl = require('readline').createInterface({
input: process.stdin,
output: process.stdout,
});
rl.on('SIGINT', function() {
process.emit('SIGINT');
});
}
process.on('SIGINT', function() {
console.log('SIGINT');
process.exit();
});
var filepath = path.resolve(__dirname, 'pid.txt');
fs.writeFile(filepath, process.pid);
var i = 0;
setInterval(function () {
console.log(i++);
}, 1000);
kill.js
'use strict';
var fs = require('fs');
var path = require('path');
var pidPath = path.resolve(__dirname, 'pid.txt');
fs.readFile(pidPath, 'utf8', function (err, data) {
if (err) {
return console.log(err);
}
process.kill(data, 'SIGINT');
});
问题:
发送process.kill(PID, 'SIGINT') 时,它实际上并没有在Windows 中将其检测为SIGINT。我可以手动运行child.js 并使用CTRL+C 来终止进程以触发SIGINT,所以我知道readline 代码正在工作(或者可能不会因为SIGINT 将在没有readline 代码的情况下触发,但它仍然会触发SIGINT)
process.kill() 不会将信号类型发送到分离的进程吗?如何检测到一个单独的脚本正试图终止我的子进程并正常关闭?
【问题讨论】:
-
试试这个:
spawn("taskkill", ["/pid", child.pid, '/f', '/t']); -
@Louy 不重复,因为在该问题中,返回对子进程的引用,但这是从完全不同的节点进程中杀死子进程。此外,我已经在使用
spawn,正如接受的答案中所建议的那样。 -
Windows 没有信号。 Node.js 可能会模拟跨进程信号,但这样做并不常见。
-
为了澄清最后一条评论,windows 上的 process.kill 似乎可能会忽略信号类型,而只是终止目标进程。
标签: node.js windows command-line-interface kill