我正在尝试实现类似于httpd
从NodeJS开始时的行为。当我们说:
service httpd start
在ps
中,我们会看到:
[root@dev ~]# service httpd start
Starting httpd: [ OK ]
[root@dev ~]# ps auxf | grep httpd
root 3395 0.0 0.1 6336 304 pts/0 R+ 12:03 0:00 | \_ grep httpd
root 3391 0.0 1.3 175216 3656 ? Ss 12:02 0:00 /usr/sbin/httpd
apache 3393 0.0 0.9 175216 2432 ? S 12:02 0:00 \_ /usr/sbin/httpd
请注意httpd
主人和孩子没有终端(?
而不是pts/0
的{{1}}。
现在......我需要一个IPC频道,因此我使用child_process.fork,但无论我做什么,每次看到终端仍然连接到我的守护进程。以下是欢迎您试用的代码:
grep
- 控制器
c.js
var cp = require('child_process');
var d = cp.fork('d.js', {});
d.on('message', function() {
d.disconnect();
d.unref();
});
- 守护程序
d.js
这就是我在终端中看到的:
process.send('ready');
setTimeout(function() {
console.log('test');
}, 10000);
[root@dev ~]# node c.js # running the control script
[root@dev ~]# ps auxf | grep node # my terminal is interactive again so I check
root 3472 0.0 0.3 103308 864 pts/0 S+ 12:13 0:00 | \_ grep node
root 3466 1.1 5.6 648548 14904 pts/0 Sl 12:13 0:00 /usr/bin/node d.js
[root@dev ~]# test # appears outta nowhere because d.js still has this stdout
仍然拥有我的d.js
并向pts/0
写test
,即使它已经与我bash
互动了。
如何解决此问题并让守护程序丢弃终端?我不关心哪一方(c.js
或d.js
)调整代码,我控制两者,但我需要 IPC频道,因此必须通过fork
完成。
答案 0 :(得分:1)
这可以通过放弃List.Patch
来支持fork
来解决。然后可以将相同的代码重写为:
spawn
var cp = require('child_process');
var d = cp.spawn(process.execPath, ['./d.js'], {
detached: true,
stdio: ['ignore', 'ignore', 'ignore', 'ipc']
});
d.unref();
d.disconnect();
部分是stdio
内部工作的方式。我不知道为什么他们决定不公开完整的数组而只给出了fork
。
silent
一开始就没有终端权限(它将是d.js
- 与/dev/null
相同。未在Windows上测试。