捕捉 SIGTERM 与捕捉 SIGINT
Posted
技术标签:
【中文标题】捕捉 SIGTERM 与捕捉 SIGINT【英文标题】:Catching SIGTERM vs catching SIGINT 【发布时间】:2017-07-15 23:39:23 【问题描述】:在 Node.js 服务器中,捕捉 SIGTERM 和捕捉 SIGINT 有什么区别吗?
我认为进程不应该能够防止在收到 SIGINT 时关闭?
process.once('SIGINT', function (code)
console.log('SIGINT received...');
server.close();
);
// vs.
process.once('SIGTERM', function (code)
console.log('SIGTERM received...');
server.close();
);
我能否捕获两个信号并阻止退出?我的实验表明答案是肯定的,但根据我的阅读,SIGINT 总是假设关闭一个进程。
或者我把 SIGINT 和 SIGKILL 混淆了?也许 SIGKILL 是我无法恢复的信号?
捕获这些信号当然可以让我优雅地关机:
server.once('close', function()
// do some other stuff
process.exit(2); // or whatever code pertains
);
我认为我将 SIGINT 与 SIGKILL 混淆了 -
如果我尝试这样做:
process.once('SIGKILL', function (code)
console.log('SIGKILL received...');
exitCode = code || 2;
server.close();
);
我收到此错误:
internal/process.js:206
throw errnoException(err, 'uv_signal_start');
^
Error: uv_signal_start EINVAL
at exports._errnoException (util.js:1022:11)
at process.<anonymous> (internal/process.js:206:15)
at emitTwo (events.js:106:13)
at process.emit (events.js:191:7)
at _addListener (events.js:226:14)
at process.addListener (events.js:275:10)
at process.once (events.js:301:8)
所以显然你不能捕获 SIGKILL 信号,但你可以捕获 SIGINT 和 SIGTERM?
【问题讨论】:
【参考方案1】:接受的答案是错误的。
-
来自https://en.wikipedia.org/wiki/Unix_signal
SIGTERM SIGTERM 信号被发送到进程以请求其终止... SIGINT 几乎与 SIGTERM 相同。
-
命令
kill
周围的描述不正确。
您可以同时捕获它们,并且仍然可以使用 SIGKILL - kill -9 pid 关闭进程
错了。同样,来自上面的 wiki:
SIGKILL 信号被发送到进程以使其立即终止(终止)。与 SIGTERM 和 SIGINT 相比,这个信号不能被捕获或忽略,并且接收进程在接收到这个信号时不能执行任何清理。
总之,
SIGINT 几乎与 SIGTERM 相同。
【讨论】:
我认为措辞有些混乱。 “您可以同时捕获它们(SIGINT 和 SIGTERM),并且仍然可以使用SIGKILL
- kill -9 pid
关闭进程”。这种说法是正确的。公认的答案是正确的。
我的意思是抓住其中任何一个(SIGINT 和 SIGTERM)与 SIGKILL 无关。 IE。您是否需要捕获其中任何一个(SIGINT 和 SIGTERM)才能使用SIGKILL - kill -9 pid
关闭进程才能工作? @蓝
嗯,是的,它们是三种不同的信号。您可以捕获 SIGINT 和 SIGTERM,然后做任何事情,仍然被 SIGKILL 杀死。您不必这样做,但 OP 要求澄清信号之间的差异。给定的场景就是这样。您可以忽略 SIGINT 和 SIGTERM,但不能忽略 SIGKILL。这里没有人真的错了,哈哈。
同意,但我认为OP有更好的总结,“你不能trap SIGKILL信号,但你可以trap SIGINT和SIGTERM?” 应该承认,而不是被模糊。
它们必须不同的原因是因为SIGTERM专门发生在程序应该终止的时候。 SIGINT 只是意味着用户按下了 ctrl+c,这有时意味着终止,但并非总是如此。例如,在 VIM 中,ctrl+c 可能是在编辑器中使用的实际命令,因此 SIGINT 仅用于告诉 VIM“哦,用户的意思是 ctrl+c”。或者,考虑 bash 本身。当你 ctrl+c,即给 bash 一个 SIGINT 时,bash 的工作是获取任何正在运行的进程,并给 that 程序 SIGINT(可能是任何程序)。如果你给 bash SIGTERM,它会死。【参考方案2】:
来自https://en.wikipedia.org/wiki/Unix_signal:
SIGINT
由用户按Ctrl+C生成,是interrupt
SIGTERM
是发送来请求进程终止的信号。 kill 命令发送一个SIGTERM
,它是一个terminate
您可以同时捕获SIGTERM
和SIGINT
,并且始终可以使用SIGKILL
或kill -9 [pid]
关闭进程。
【讨论】:
以上是关于捕捉 SIGTERM 与捕捉 SIGINT的主要内容,如果未能解决你的问题,请参考以下文章