Node.js多進程基礎
Node.js 是以單線程的模式運行的,但它使用的是事件驅動來處理并發。這樣有助于我們在多核 cpu 的系統上創建多個子進程,從而提高性能。
每個子進程總是帶有三個流對象:child.stdin, child.stdout 和child.stderr。他們可能會共享父進程的 stdio 流,或者也可以是獨立的被導流的流對象。
Node提供了 child_process 模塊來創建子進程,方法有:
exec-child_process.exec使用子進程執行命令,緩存子進程的輸出,并將子進程的輸出以回調函數的形式返回。
spawn-child_process.spawn使用指定的命令行參數創建進程。
fork-child_process.fork是spawn()的特殊形式,用于在子進程中運行模塊,與spawn方法不同的是,fork會在父進程與子進程之間,建立一個通信管道,用于進程之間的通信。
1、exec() 方法
child_process.exec(command[, options], callback)
support.py 文件代碼:
# -*- coding: utf-8 -*-
import sys
print("進程 " +sys.argv[1] +" 執行。")
master.js 文件代碼:
const fs = require('fs');
const child_process = require('child_process');
for(var i=0; i<3; i++) {
//創建三個子進程
var workerProcess = child_process.exec('python support.py '+i, function (error, stdout, stderr) {
if (error) {
console.log(error.stack);
console.log('Error code: '+error.code);
console.log('Signal received: '+error.signal);
}
console.log('stdout: ' + stdout);
console.log('stderr: ' + stderr);
});
workerProcess.on('exit', function (code) {
console.log('子進程已退出,退出碼 '+code);
});
}
2、spawn()方法
child_process.spawn(command[, args][, options])
support.py 文件代碼:
# -*- coding: utf-8 -*-
import sys
print("進程 " +sys.argv[1] +" 執行。")
master.js 文件代碼:
const fs = require('fs');
const child_process = require('child_process');
for(var i=0; i<3; i++) {
var workerProcess = child_process.spawn('python', ['support.py', i]);
workerProcess.stdout.on('data', function (data) {
console.log('stdout: ' + data);
});
workerProcess.stderr.on('data', function (data) {
console.log('stderr: ' + data);
});
workerProcess.on('close', function (code) {
console.log('子進程已退出,退出碼 '+code);
});
}
3、fork()方法
child_process.fork(modulePath[, args][, options])
modulePath: String,將要在子進程中運行的模塊
support.js 文件代碼:
console.log("進程 " + process.argv[2] + " 執行。" );
master.js 文件代碼:
const fs = require('fs');
const child_process = require('child_process');
for(var i=0; i<3; i++) {
var worker_process = child_process.fork("support.js", [i]);
worker_process.on('close', function (code) {
console.log('子進程已退出,退出碼 ' + code);
});
}
node調用python
見上述1、exec()方法和spawn()方法。
比較exec和spawn
1、exec將子進程輸出結果暫放在buffer中,在結果完全返回后,再將輸出一次性的以回調函數返回。如果exec的buffer體積設置的不夠大,它將會以一個“maxBuffer exceeded”錯誤失敗告終。而spawn在子進程開始執行后,就不斷的將數據從子進程返回給主進程,它沒有回調函數,它通過流的方式發數據傳給主進程,從而實現了多進程之間的數據交換。這個功能的直接用應用場景就是“系統監控”。
2、書寫上,exec更方便一些,將整個命令放在第一個參數中,而spqwn需要拆分。
child_process.spawn('python', ['support.py', i])
child_process.exec('python support.py '+i, callback)
參考資料