Child Processes in Node.js
Run shell commands and external programs from Node.js.
Child Processes
Need to run shell commands from Node.js? Use child processes.
exec() - Simple Commands
```javascript const { exec } = require('child_process');
exec('ls -la', (error, stdout, stderr) => { if (error) { console.error('Error:', error.message); return; } console.log(stdout); }); ```
**Use case:** Running simple commands like `git status`, `ls`, `pwd`
spawn() - For Large Output
```javascript const { spawn } = require('child_process');
const ls = spawn('ls', ['-la', '/usr']);
ls.stdout.on('data', (data) => { console.log(`${data}`); });
ls.on('close', (code) => { console.log(`Exited with code ${code}`); }); ```
**Difference:** - `exec()` buffers entire output in memory - `spawn()` streams output in chunks
fork() - Run Node.js Files
```javascript const { fork } = require('child_process');
const worker = fork('./worker.js');
worker.send({ task: 'calculate', numbers: [1,2,3,4,5] });
worker.on('message', (result) => { console.log('Result:', result); }); ```
```javascript // worker.js process.on('message', (msg) => { const sum = msg.numbers.reduce((a, b) => a + b, 0); process.send({ sum }); }); ```
**Use case:** Heavy computations that would block main thread
Real Example: Image Processing
```javascript const { spawn } = require('child_process');
function compressImage(input, output) { return new Promise((resolve, reject) => { const convert = spawn('convert', [ input, '-quality', '80', output ]); convert.on('close', (code) => { if (code === 0) resolve(); else reject(new Error('Failed')); }); }); }
await compressImage('photo.jpg', 'photo-small.jpg'); ```
Real Example: Git Operations
```javascript const { exec } = require('child_process'); const { promisify } = require('util'); const execPromise = promisify(exec);
async function getGitStatus() { const { stdout } = await execPromise('git status'); return stdout; }
async function commitChanges(message) { await execPromise('git add .'); await execPromise(`git commit -m "${message}"`); }
const status = await getGitStatus(); console.log(status); ```
Security Warning
```javascript const userInput = req.query.filename; exec(`cat ${userInput}`); ```
**Never do this!** User can inject: `file.txt; rm -rf /`
Safe version:
```javascript const { spawn } = require('child_process'); const cat = spawn('cat', [userInput]); ```
When to Use What
``` exec() → Simple commands, small output spawn() → Large output, streaming data fork() → Heavy Node.js computations ```
Key Takeaway
Child processes let you run external commands from Node.js. Use `spawn` for large outputs, `fork` for Node.js scripts, `exec` for simple commands. Always validate user input to prevent command injection.