gpt4 book ai didi

node.js - 当将标准输入管道传输到子进程时,NodeJS 进程永远不会结束

转载 作者:太空宇宙 更新时间:2023-11-03 22:34:22 24 4
gpt4 key购买 nike

我正在使用 spawn 创建子进程并管道数据:

child process  |  parent process (main)
---------------------------------------
stdout -----> process.stdout
stderr -----> process.stderr
stdin <----- process.stdin

问题在于,当通过管道将process.stdin传递给子进程stdin时,当子进程完成时,主进程并未结束。

代码如下所示(我猜这不是一个很好的例子,因为 ps 不使用 stdin 数据):

var Spawn = require("child_process").spawn;

var ps = Spawn("ps");
process.stdin.pipe(ps.stdin);
ps.stdout.pipe(process.stdout);
ps.stderr.pipe(process.stderr);

如果我删除 process.stdin.pipe(ps.stdin) 行,主进程就会结束,但 stdin 数据不再通过管道传输。

为什么ps子进程结束时主进程没有结束?我该如何解决这个问题?

一个丑陋的解决方案是:

ps.on("close", process.exit.bind(process));

我不喜欢这样,因为我真的不想强制关闭主进程,但我想自然地关闭(例如,使用 setTimeout(function( ){}, 1000) 您等待 1000 毫秒,然后进程结束)。

最佳答案

我不知道这是否是 Node 中的错误或预期行为,但有几个解决方法,其中之一可能适合您。

如果您当前的进程应该在子进程终止时恰好终止,您可以简单地为 exit 添加一个处理程序,如下所示:

const fail = err => { throw err }
ps.on("exit", (code, signal) => code !== null ? process.exit(code) : signal !== null ? process.kill(process.pid, signal) : fail("Impossible situation, child process neither exited nor was killed"))

这将绕过我们的问题,因为 stdin 流坐在那里支撑着一切。

如果您确实需要在当前进程中执行更多操作而不仅仅是运行该子进程,则这种方法可能 Not Acceptable 。当您意识到当前进程应该做的所有工作都已完成时,您可以做的是 destroy process.stdin 。例如,如果您想要运行的只是 ps,您可以添加:

ps.on("exit", (...) => {
...
process.stdin.destroy()
})

这将具有相同的效果。如果在 ps 失效后您需要做更多工作,您可以将相同的事情放入其他适当的事件处理程序中。

关于node.js - 当将标准输入管道传输到子进程时,NodeJS 进程永远不会结束,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31716784/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com