all files / lib/ file-writer.js

16.92% Statements 11/65
0% Branches 0/34
0% Functions 0/10
18.97% Lines 11/58
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108                                                                                                                                                                                                  
module.exports = FileWriter
 
var fs = require('graceful-fs')
var Writer = require('./writer.js')
var inherits = require('inherits')
var EOF = {}
 
inherits(FileWriter, Writer)
 
function FileWriter (props) {
  var self = this
  if (!(self instanceof FileWriter)) {
    throw new Error('FileWriter must be called as constructor.')
  }
 
  // should already be established as a File type
  if (props.type !== 'File' || !props.File) {
    throw new Error('Non-file type ' + props.type)
  }
 
  self._buffer = []
  self._bytesWritten = 0
 
  Writer.call(this, props)
}
 
FileWriter.prototype._create = function () {
  var self = this
  if (self._stream) return
 
  var so = {}
  if (self.props.flags) so.flags = self.props.flags
  so.mode = Writer.filemode
  if (self._old && self._old.blksize) so.bufferSize = self._old.blksize
 
  self._stream = fs.createWriteStream(self._path, so)
 
  self._stream.on('open', function () {
    // console.error("FW open", self._buffer, self._path)
    self.ready = true
    self._buffer.forEach(function (c) {
      if (c === EOF) self._stream.end()
      else self._stream.write(c)
    })
    self.emit('ready')
    // give this a kick just in case it needs it.
    self.emit('drain')
  })
 
  self._stream.on('error', function (er) { self.emit('error', er) })
 
  self._stream.on('drain', function () { self.emit('drain') })
 
  self._stream.on('close', function () {
    // console.error('\n\nFW Stream Close', self._path, self.size)
    self._finish()
  })
}
 
FileWriter.prototype.write = function (c) {
  var self = this
 
  self._bytesWritten += c.length
 
  if (!self.ready) {
    if (!Buffer.isBuffer(c) && typeof c !== 'string') {
      throw new Error('invalid write data')
    }
    self._buffer.push(c)
    return false
  }
 
  var ret = self._stream.write(c)
  // console.error('\t-- fw wrote, _stream says', ret, self._stream._queue.length)
 
  // allow 2 buffered writes, because otherwise there's just too
  // much stop and go bs.
  if (ret === false && self._stream._queue) {
    return self._stream._queue.length <= 2
  } else {
    return ret
  }
}
 
FileWriter.prototype.end = function (c) {
  var self = this
 
  if (c) self.write(c)
 
  if (!self.ready) {
    self._buffer.push(EOF)
    return false
  }
 
  return self._stream.end()
}
 
FileWriter.prototype._finish = function () {
  var self = this
  if (typeof self.size === 'number' && self._bytesWritten !== self.size) {
    self.error(
      'Did not get expected byte count.\n' +
      'expect: ' + self.size + '\n' +
      'actual: ' + self._bytesWritten)
  }
  Writer.prototype._finish.call(self)
}