Node Core Modules Exploration - Child Processes
Previously on blog, i gave a little, and i mean little, overview of what C/C++ Addons are. Now onto Child Processes
Child Process
This is a pretty cool module. The basic gist of the module, is that it allows you to run commands from inside your node.js programs.
Like other modules, we need to require it, but we don’t actually create instances of ChildProcess
directly. We use the spawn
, fork
, exec
, or execFile
methods to create new instances.
These methods are Asynchronous and there are synchronous version also.
While there are a few different functions, they all pretty much build upon 1 main function, child_process.spawn
Lets see a quick example of spawn
, first we get a new instance:
const spawn = require('child_process').spawn;
Then we give it a command to execute:
const ls = spawn('ls', ['-ltra']);
spawn
actually takes 3 arguments.
The first is the command we want to run.
The second is an Array of the arguments we want to pass to the command. In this case we are passing -ltra
The third argument is an object of options, like setting the current working directory, cwd
, and things of that nature.
The new process ls
that is spawned, will have stdout
, stderr
and stdin
ReadStreams Event Emitter thingies, so you can then listen for data to come in on them.
ls.stdout.on('data', (d) => {
console.log(`stdout: ${d}`);
});
Well, thats nice, but what about these other functions. It would be nice if we didn’t have to listen for these .on
events and just provide a callback.
This is where the .exec
function would be used.
It is essentially the same as using spawn
, but you can specfiy a callback
exec
also has 3 arguments, but they are slightly different.
The first is the command, but this time you actually add the arguments to the command.
The second is the options
object
The third is the callback.
So taking that previous example.
const exec = require('child_process').exec;
exec('ls -ltra', (error, stdout, stderr) => {
console.log(stdout);
});
The execFile
is essentially a combination of spawn
and exec
.
There are 4 arguments this time.
The first is the command,
The second is the array of arguments.
The third is the options
object
The fourth is the callback.
The difference here is it doesn’t actually open a new shell when being executed, so it is slightly more effecient. That is unless you are on windows, then you can’t really use that.
Check out the docs for why that is
Getting Forking Crazy
Then there is this other crazy little function fork
It is much like spawn
, but this will actually take a module, and execute it in a totally seperate Node instance with it’s own instance of V8 and memory. So needless to say, be careful with this one.
Another neat thing, is that a communication channel gets added to the returned ChildProcess, so you can pass messsages back and forth between the Parent and the forked processes.
Lets take a look at simple example of using the fork
function.
The parent:
const cp = require('child_process').fork;
const forked = fork('child.js');
forked.send({message: 'YO'});
forked.on('message', (m) => {
console.log(`Child Message: ${m.message}`);
});
And the child.js file:
process.on('message', (m) => {
console.log(`Parent Message: ${m.message}`);
process.send({message: 'Back At Ya'});
});
There are some more sophisticated things that you can do with fork, so check out the docs.
Next time we will take a look at the cluster
module.