Understand file descriptors and nodejs

file-descriptorsnode.js

I'm having a bit of a confused time understanding what a file descriptor is and if I even need one! I am trying to spawn a process in nodejs and have its out put be written directly to an out put file.

I understand my question is specific to a language outside the scope of the unix family but I believe my problem is coming from me not understanding some thing about the system and not the language.

This is the function I am calling from my script. I assumed I could call it in such a way

require('child_process').spawn('./my_script.bash 1>out.txt')

No luck though! I know that the script is executing and that its working.

Best Answer

The spawn command returns a readable stream, so you will need to pipe that to a writable stream to do something useful.

Piping to a file

// the filed module makes simplifies working with the filesystem
var filed = require('filed')
var path = require('path')
var spawn = require('spawn')
var outputPath = path.join(__dirname, 'out.txt')

// filed is smart enough to create a writable stream that we can pipe to
var writableStream = filed(outputPath)

var cmd = path.join(__dirname, 'my_script.bash')
var args = [] // you can option pass arguments to your spawned process
var child = spawn(cmd, args)

// child.stdout and child.stderr are both streams so they will emit data events
// streams can be piped to other streams
child.stdout.pipe(writableStream)
child.stderr.pipe(writableStream)

child.on('error', function (err) {
  console.log('an error occurred')
  console.dir(err)
})

// code will be the exit code of your spawned process. 0 on success, a positive integer on error
child.on('close', function (code) {
  if (code !== 0) {
  console.dir('spawned process exited with error code', code)
    return
  }
  console.dir('spawned process completed correctly at wrote to file at path', outputPath)
})

You will need to install the filed module to run the example above

npm install filed

Piping to stdout and stderr

process.stdout and process.stderr are both writable streams so you can pipe the output of your spawned command directly to the console as well

var path = require('path')
var spawn = require('spawn')
var cmd = path.join(__dirname, 'my_script.bash')
var args = [] // you can option pass arguments to your spawned process
var child = spawn(cmd, args)

// child is a stream so it will emit events
child.stderr.pipe(process.stderr)
child.stdout.pipe(process.stderr)

child.on('error', function (err) {
  console.log('an error occurred')
  console.dir(err)
})

// code will be the exit code of your spawned process. 0 on success, a positive integer on error
child.on('close', function (code) {
  if (code !== 0) {
  console.dir('spawned process exited with error code', code)
    return
  }
  console.dir('spawned process completed correctly at wrote to file at path', outputPath)
})
Related Question