Permalink
Browse files

[dist] 0.1.0 first release

  • Loading branch information...
0 parents commit 1fc9da7523a79dd8ee519928fcfcfccd927364c4 @bmeck committed Dec 20, 2012
@@ -0,0 +1,5 @@
+/node_modules
+.DS_Store
+.swp
+.svn
+
@@ -0,0 +1,50 @@
+#!/usr/bin/env node
+//
+// dogfood.js file-a file-b file-c
+//
+// A simple dogfooding service to pipe data in memory from a writer to a reader
+//
+var fs = require('fs');
+var tart = require('./lib/index.js');
+var TarWriter = tart.TarWriter;
+var TarReader = tart.TarReader;
+
+var IN_FILES = process.argv.slice(2);
+
+var writer = new TarWriter();
+//
+// Piping a writer to a reader for simple dogfooding
+//
+new TarReader(writer.stream).on('entry', function (record, stream) {
+ var path = record.get('path');
+ console.log('FOUND ENTRY FOR:', path);
+ //
+ // We can dump or manipulate the data here, rewrite it if we want to and pipe it to a new writer
+ //
+ stream.on('data', function (data) {
+ console.log('DATA:', data.toString())
+ })
+});
+
+var togo = IN_FILES.length;
+if (!togo) {
+ writer.end();
+}
+IN_FILES.forEach(function (IN_FILE) {
+ var content = fs.readFileSync(IN_FILE).toString();
+ console.log('WRITING:', IN_FILE)
+ //
+ // Simple file creation
+ //
+ writer.createFile({
+ path: IN_FILE,
+ size: content.length
+ },function (err, stream) {
+ stream.end(content);
+
+ togo--;
+ if (!togo) {
+ writer.end();
+ }
+ });
+});
@@ -0,0 +1,5 @@
+exports.TarRecord = require('./record/tar.js').TarRecord;
+exports.GNUTarRecord = require('./record/gnu.js').GNUTarRecord;
+exports.UStarRecord = require('./record/ustar.js').UStarRecord;
+exports.TarReader = require('./reader.js').TarReader;
+exports.TarWriter = require('./writer.js').TarWriter;
@@ -0,0 +1,135 @@
+var GNUTarRecord = require('./record/gnu.js').GNUTarRecord;
+var UStarRecord = require('./record/ustar.js').UStarRecord;
+var EventEmitter = require('events').EventEmitter;
+var subStream = require('./substream').subStream;
+
+function TarReader(rstream) {
+ var self = this;
+ EventEmitter.call(self);
+ self.stream = rstream;
+ self._couldEnd = false;
+ self._pax = null;
+ self._buffered = '';
+ self.globalPax = {};
+ self.localPax = {};
+ self.stream.on('readable', function () {
+ self.readChunk();
+ });
+ return self;
+}
+require('util').inherits(TarReader, EventEmitter);
+TarReader.prototype.readChunk = function () {
+ var data = this.stream.read(512);
+ if (data) {
+ this.onChunk(data);
+ }
+}
+TarReader.prototype.onChunk = TarReader.prototype.onHeaderChunk = function (header) {
+ var self = this;
+ function gotoHeader() {
+ self.onChunk = self.onHeaderChunk;
+ self.readChunk();
+ }
+ if (header.slice(257, 263).toString() === 'ustar\x00') {
+ self._couldEnd = false;
+ var record = new UStarRecord(header);
+ switch (record.get('type')) {
+ case 'g':
+ self._pax = self.globalPax;
+ break;
+ case 'x':
+ self._pax = self.localPax;
+ break;
+ default:
+ var stream = self.readContent(self._addPax(record), gotoHeader);
+ self.emit('entry', record, stream);
+ return;
+ }
+ self.onChunk = this.onPaxChunk;
+ self.readChunk();
+ }
+ else if (header.slice(257, 263).toString() === '\x00\x00\x00\x00\x00\x00') {
+ if (self._couldEnd) {
+ self.emit('end');
+ }
+ else {
+ self._couldEnd = true;
+ self.readChunk();
+ }
+ }
+ else {
+ self._couldEnd = false;
+ var record = new GNUTarRecord(header);
+ var stream = this.readContent(record, gotoHeader);
+ self.emit('entry', record, stream);
+ }
+}
+TarReader.prototype.onPaxChunk = function (data) {
+ var lengthPattern = /\d+(?=\D)/g;
+ this._buffered += data;
+ var match = lengthPattern.exec(this._buffered);
+ var index = 0;
+ while (match) {
+ var length = +match[0];
+ index = match.index;
+ var end = index + length;
+ if (this._buffered.length < end) {
+ this.readChunk();
+ return;
+ }
+ else {
+ var str = this._buffered.substring(index + match[0].length, end).trim();
+ var key_and_value = /([^=]*)[=](.*)/.exec(str);
+ var key = key_and_value[1];
+ var value = key_and_value[2];
+ this._pax[key] = value;
+ lengthPattern.lastIndex = end;
+ match = lengthPattern.exec(this._buffered);
+ }
+ }
+ this.onChunk = this.onHeaderChunk;
+ this.readChunk();
+}
+TarReader.prototype._addPax = function (record) {
+ var combinedPax = {};
+ var globalPax = this.globalPax;
+ var localPax = this.localPax;
+ var usePax = false, usedLocalPax = false;
+ Object.keys(globalPax).forEach(function (name) {
+ if (name in localPax) {
+ return;
+ }
+ usePax = true;
+ combinedPax[name] = globalPax[name];
+ });
+ Object.keys(localPax).forEach(function (name) {
+ usePax = usedLocalPax = true;
+ combinedPax[name] = localPax[name];
+ });
+ if (usePax) {
+ record.pax = combinedPax;
+ if (usedLocalPax) {
+ this.localPax = {};
+ }
+ }
+ return record;
+}
+TarReader.prototype.readContent = function (record, cb) {
+ var length = +record.get('size');
+ //
+ // pad to 512 block
+ //
+ var paddedLength = length;
+ if (length % 512) {
+ paddedLength += 512 - (length % 512);
+ }
+ //
+ // Only grab the proper amount
+ //
+ var paddedStream = subStream(this.stream, paddedLength);
+ var stream = subStream(paddedStream, length);
+ paddedStream.on('finish', cb);
+ return stream;
+}
+
+exports.TarReader = TarReader;
@@ -0,0 +1,97 @@
+var TarRecord = require('./tar.js').TarRecord;
+function GNUTarRecord(buffer) {
+ TarRecord.call(this);
+ if (buffer) {
+ this._buffer = buffer.slice(0, 512);
+ }
+ else {
+ this._buffer = new Buffer(512);
+ this._buffer.fill(0);
+ }
+ return this;
+}
+require('util').inherits(GNUTarRecord, TarRecord);
+GNUTarRecord.prototype._buffer = null;
+GNUTarRecord.prototype.set = function (name, value) {
+ name = (''+name).toLowerCase();
+ switch (name) {
+ case "type":
+ this._write(value, 156, 1);
+ break;
+ case "path":
+ this._write(value, 0, 100);
+ break;
+ case "mode":
+ this._write((+value).toString(8), 100, 7, '0', true);
+ break;
+ case "mtime":
+ this._write((+value).toString(8), 136, 11, '0', true);
+ break;
+ case "size":
+ this._write((+value).toString(8), 124, 11, '0', true);
+ break;
+ case "linkpath":
+ this._write(value, 157, 100);
+ break;
+ case "uid":
+ this._write((+value).toString(8), 108, 7, '0', true);
+ break;
+ case "gid":
+ this._write((+value).toString(8), 116, 7, '0', true);
+ break;
+ default:
+ }
+}
+GNUTarRecord.prototype._write = function (value, offset, length, fill, alignRight) {
+ this._buffer.fill(fill || 0, offset, offset + length);
+ this._buffer.write(value, alignRight ? Math.max(offset + length - value.length, offset) : offset, length);
+}
+GNUTarRecord.prototype.get = function (name) {
+ switch (name) {
+ case 'path':
+ return this._read(0, 100);
+ case 'mode':
+ return this._read(100, 8);
+ case 'uid':
+ return parseInt(this._read(108, 8), 8);
+ case 'gid':
+ return parseInt(this._read(116, 8), 8);
+ case 'size':
+ return parseInt(this._read(124, 12), 8);
+ case 'mtime':
+ return parseInt(this._read(136, 12), 8);
+ case 'type':
+ return this._read(156, 1);
+ case 'linkpath':
+ return this._read(157, 100);
+ }
+ return null;
+}
+GNUTarRecord.prototype._read = function (offset, length) {
+ return this._scrubValue(this._buffer.slice(offset, offset + length)).toString();
+}
+GNUTarRecord.prototype._scrubValue = function (value) {
+ for (var i = 0; i < value.length; i++) {
+ if (value[i] === 0) {
+ break;
+ }
+ }
+ return value.slice(0, i);
+}
+GNUTarRecord.prototype.toBuffer = function () {
+ this._buffer.write('GNUTar ', 257, 6);
+ this._buffer.write('01 ', 263, 2);
+ this._doChecksum();
+ return this._buffer;
+}
+GNUTarRecord.prototype._doChecksum = function () {
+ this._buffer.write(' ', 148, 8);
+ var sum = 0;
+ for (var i = 0; i < this._buffer.length; i++) {
+ sum += this._buffer[i];
+ }
+ this._write(sum.toString(8).slice(-6), 148, 6, '0', true);
+ this._buffer.write('\x00 ', 154, 2);
+}
+
+exports.GNUTarRecord = GNUTarRecord;
@@ -0,0 +1,5 @@
+function TarRecord() {}
+TarRecord.prototype.toBuffer = function () {
+ throw new Error('not implemented');
+}
+exports.TarRecord = TarRecord;
Oops, something went wrong.

0 comments on commit 1fc9da7

Please sign in to comment.