You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
				
					
					
						
							169 lines
						
					
					
						
							3.7 KiB
						
					
					
				
			
		
		
	
	
							169 lines
						
					
					
						
							3.7 KiB
						
					
					
				module.exports = EntryWriter | 
						|
 | 
						|
var tar = require("../tar.js") | 
						|
  , TarHeader = require("./header.js") | 
						|
  , Entry = require("./entry.js") | 
						|
  , inherits = require("inherits") | 
						|
  , BlockStream = require("block-stream") | 
						|
  , ExtendedHeaderWriter | 
						|
  , Stream = require("stream").Stream | 
						|
  , EOF = {} | 
						|
 | 
						|
inherits(EntryWriter, Stream) | 
						|
 | 
						|
function EntryWriter (props) { | 
						|
  var me = this | 
						|
 | 
						|
  if (!(me instanceof EntryWriter)) { | 
						|
    return new EntryWriter(props) | 
						|
  } | 
						|
 | 
						|
  Stream.apply(this) | 
						|
 | 
						|
  me.writable = true | 
						|
  me.readable = true | 
						|
 | 
						|
  me._stream = new BlockStream(512) | 
						|
 | 
						|
  me._stream.on("data", function (c) { | 
						|
    me.emit("data", c) | 
						|
  }) | 
						|
 | 
						|
  me._stream.on("drain", function () { | 
						|
    me.emit("drain") | 
						|
  }) | 
						|
 | 
						|
  me._stream.on("end", function () { | 
						|
    me.emit("end") | 
						|
    me.emit("close") | 
						|
  }) | 
						|
 | 
						|
  me.props = props | 
						|
  if (props.type === "Directory") { | 
						|
    props.size = 0 | 
						|
  } | 
						|
  props.ustar = "ustar\0" | 
						|
  props.ustarver = "00" | 
						|
  me.path = props.path | 
						|
 | 
						|
  me._buffer = [] | 
						|
  me._didHeader = false | 
						|
  me._meta = false | 
						|
 | 
						|
  me.on("pipe", function () { | 
						|
    me._process() | 
						|
  }) | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype.write = function (c) { | 
						|
  // console.error(".. ew write") | 
						|
  if (this._ended) return this.emit("error", new Error("write after end")) | 
						|
  this._buffer.push(c) | 
						|
  this._process() | 
						|
  this._needDrain = this._buffer.length > 0 | 
						|
  return !this._needDrain | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype.end = function (c) { | 
						|
  // console.error(".. ew end") | 
						|
  if (c) this._buffer.push(c) | 
						|
  this._buffer.push(EOF) | 
						|
  this._ended = true | 
						|
  this._process() | 
						|
  this._needDrain = this._buffer.length > 0 | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype.pause = function () { | 
						|
  // console.error(".. ew pause") | 
						|
  this._paused = true | 
						|
  this.emit("pause") | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype.resume = function () { | 
						|
  // console.error(".. ew resume") | 
						|
  this._paused = false | 
						|
  this.emit("resume") | 
						|
  this._process() | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype.add = function (entry) { | 
						|
  // console.error(".. ew add") | 
						|
  if (!this.parent) return this.emit("error", new Error("no parent")) | 
						|
 | 
						|
  // make sure that the _header and such is emitted, and clear out | 
						|
  // the _currentEntry link on the parent. | 
						|
  if (!this._ended) this.end() | 
						|
 | 
						|
  return this.parent.add(entry) | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype._header = function () { | 
						|
  // console.error(".. ew header") | 
						|
  if (this._didHeader) return | 
						|
  this._didHeader = true | 
						|
 | 
						|
  var headerBlock = TarHeader.encode(this.props) | 
						|
 | 
						|
  if (this.props.needExtended && !this._meta) { | 
						|
    var me = this | 
						|
 | 
						|
    ExtendedHeaderWriter = ExtendedHeaderWriter || | 
						|
      require("./extended-header-writer.js") | 
						|
 | 
						|
    ExtendedHeaderWriter(this.props) | 
						|
      .on("data", function (c) { | 
						|
        me.emit("data", c) | 
						|
      }) | 
						|
      .on("error", function (er) { | 
						|
        me.emit("error", er) | 
						|
      }) | 
						|
      .end() | 
						|
  } | 
						|
 | 
						|
  // console.error(".. .. ew headerBlock emitting") | 
						|
  this.emit("data", headerBlock) | 
						|
  this.emit("header") | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype._process = function () { | 
						|
  // console.error(".. .. ew process") | 
						|
  if (!this._didHeader && !this._meta) { | 
						|
    this._header() | 
						|
  } | 
						|
 | 
						|
  if (this._paused || this._processing) { | 
						|
    // console.error(".. .. .. paused=%j, processing=%j", this._paused, this._processing) | 
						|
    return | 
						|
  } | 
						|
 | 
						|
  this._processing = true | 
						|
 | 
						|
  var buf = this._buffer | 
						|
  for (var i = 0; i < buf.length; i ++) { | 
						|
    // console.error(".. .. .. i=%d", i) | 
						|
 | 
						|
    var c = buf[i] | 
						|
 | 
						|
    if (c === EOF) this._stream.end() | 
						|
    else this._stream.write(c) | 
						|
 | 
						|
    if (this._paused) { | 
						|
      // console.error(".. .. .. paused mid-emission") | 
						|
      this._processing = false | 
						|
      if (i < buf.length) { | 
						|
        this._needDrain = true | 
						|
        this._buffer = buf.slice(i + 1) | 
						|
      } | 
						|
      return | 
						|
    } | 
						|
  } | 
						|
 | 
						|
  // console.error(".. .. .. emitted") | 
						|
  this._buffer.length = 0 | 
						|
  this._processing = false | 
						|
 | 
						|
  // console.error(".. .. .. emitting drain") | 
						|
  this.emit("drain") | 
						|
} | 
						|
 | 
						|
EntryWriter.prototype.destroy = function () {}
 | 
						|
 |