Skip to content
导航

子进程

node:child_process 模块用于创建子进程。

主进程和子进程是不同的进程,每个进程至少有一个线程,一个线程只属于一个进程。因此使用子进程可以实现多线程并行工作。

创建子进程

有4种方法异步创建子进程:

  • exec
  • execFile
  • spawn
  • fork

以及除 fork 外,3种同步方法创建子进程:

  • execSync
  • execFileSync
  • spawnSync

同步方法创建子进程,将会阻塞主进程,直到子进程结束。

exec

exec( command, options, callback ) 方法运行后,先生成一个shell,然后在shell中运行command,符合开发者使用shell的习惯。

execexecFile 对参数用法的简单封装,见child_process源码

js
const childProcess = require('child_process')
childProcess.exec('node -v', {}, (error, stdout, stderr)=>{
  process.stdout.write(stdout)
})

运行后在控制台打印出 node 版本号

execFile

execFile(file, args, options, callback) 方法运行后,默认不生成shell,从环境变量中找到file并运行。

API及参数名很像是执行文件用的,但实际运行是由 spawn 实现,区别是一些预设参数,以及运行结束后执行回调 callback。使用 execexecFile 的好处主要是可以简单地设置回调函数 callback ,无需再像child_process源码一样多处设置监听。

js
const childProcess = require('child_process')
childProcess.execFile('node', ['-v'], {}, (error, stdout, stderr)=>{
  process.stdout.write(stdout)
})

运行后在控制台打印出 node 版本号

spawn

spawn(command, args, options) 运行后返回子进程实例,借此可以与子进程通信、读取子进程的输出、结束子进程等,是功能最多的创建子进程方法。

js
const childProcess = require('child_process')
const child = childProcess.spawn('node', ['-v'], {stdio: 'inherit'})
child.on('exit', ()=> console.log('child exits.'))

运行后在控制台打印出 node 版本号,并在运行结束时打印 child exits.

fork

fork(modulePath, args, options) 运行效果相当于 spawn('node', [modulePath, ...args], options)

fork 创建的子进程,其 child.stdio 默认值相当于 inherit 而不是 spawn 的默认值 pipe,即控制台输出将打印到主进程。

准备运行用的JS文件如下

js
// app.js
console.log(process.argv.slice(2))

使用 fork 创建子进程

js
const childProcess = require('child_process')
const child = childProcess.fork('app.js', ['hello'], {})
child.on('exit', ()=> console.log('child exits.'))

运行后在控制台打印出传入的参数 ['hello'],并在运行结束时打印 child exits.

参考资料