如何将一个node.js模块作为一个子进程在另一个node.js程序中执行?

53

这是我的问题。我实现了一个作为node.js模块的进行一些重计算的小脚本。所以,如果我输入“node myModule.js”,它会计算一秒钟,然后返回一个值。 现在,我想从我的主要Node.JS程序中使用该模块。我可以将所有的计算都放在一个“doSomeCalculation”函数中,然后执行:

var myModule = require("./myModule");
myModule.doSomeCalculation();

但这样会阻塞,所以不好。我想以非阻塞的方式使用它,例如像原生的数据库调用一样。因此我尝试使用child_process.spawn和exec,就像这样:

var spawn = require("child_process").spawn;
var ext = spawn("node ./myModule.js", function(err, stdout, stderr) { /* whatevs */ });
ext.on("exit", function() { console.log("calculation over!"); });

当然,它不起作用。我尝试在myModule中使用EventEmitter,触发“calculationDone”事件,并尝试在上面的示例中的“ext”变量上添加相关监听器。但仍然不起作用。

至于分叉,它们并不是我想做的事情。分叉需要将与计算相关的代码放在主程序中,进行分叉,在子进程中进行计算,而父进程则执行其任务,那么如何返回结果呢?

所以这是我的问题:当计算被放入一个Node文件中时,我能否使用子进程进行一些非阻塞计算,或者这是不可能的?我应该在Python脚本中进行繁重的计算吗?在两种情况下,如何将参数传递给子进程-例如,一个图像?


7
下午好?在其他地方可能是早上(甚至更糟!) :) - Aleksei Zabrodskii
2个回答

133

我认为你需要的是child_process.fork() API。

例如,如果你有以下两个文件:

在main.js中:

var cp = require('child_process');
var child = cp.fork('./worker');

child.on('message', function(m) {
  // Receive results from child process
  console.log('received: ' + m);
});

// Send child process some work
child.send('Please up-case this string');

在 worker.js 文件中:

process.on('message', function(m) {
  // Do work  (in this case just up-case the string
  m = m.toUpperCase();

  // Pass results back to parent process
  process.send(m.toUpperCase(m));
});

然后运行主程序(并为worker.js代码生成一个子工作进程...)

$ node --version
v0.8.3

$ node main.js 
received: PLEASE UP-CASE THIS STRING

13
如果你从另一个位置运行 main.js,为了使它正常工作,最好将调用改为 cp.fork(__dirname + '/worker'); - CodeManX

4
无论作为一个孩子你将使用什么编程语言(Node、Python、或者其他),对于Node来说都无所谓。只要确保你的计算脚本在所有操作完成并将结果写入stdout之后退出即可。
之所以无法正常工作是因为你使用了spawn而不是exec

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接