Skip to content

Instantly share code, notes, and snippets.

@chrisdickinson
Created March 30, 2011 22:08
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save chrisdickinson/f8533ff57844b1e54558 to your computer and use it in GitHub Desktop.
Save chrisdickinson/f8533ff57844b1e54558 to your computer and use it in GitHub Desktop.
// Helper Functions:
// responder - returns a function that takes arguments to close over and returns
// a function bound to `this`.
var responder = function(fn) {
return function() {
var closed = [].slice.call(arguments);
return function() {
return fn.apply(this, closed.concat([].slice.call(arguments)));
}.bind(this);
};
};
// emitterize - turn a normal `fs.something(callback)` function into one that returns
// an `EventEmitter`.
var EventEmitter = require('events').EventEmitter;
var emitterize = function(fn) {
return function() {
var ee = new EventEmitter();
fn.apply({}, [].call(arguments).concat([function(err, data) {
if(err) ee.emit('error', err);
else ee.emit('data', data);
}]));
return ee;
};
};
// The meat of the validator code:
var fs = require('fs');
var path = require('path');
var stat = emitterize(fs.stat);
var readFile = emitterize(fs.readFile);
var RepoPathValidator = function(basePath) {
EventEmitter.call(this);
this.basePath = path.join(basePath, '.git');
this.objectsPath = path.join(this.basePath, 'objects');
this.indexFilePath = path.join(this.basePath, 'index');
this.headFilePath = path.join(this.basePath, 'HEAD');
stat(this.basePath).
on('data', this.baseDirOkay()).
on('error', this.emit.bind(this, 'error'));
};
RepoPathValidator.prototype = new EventEmitter();
RepoPathValidator.prototype.baseDirOkay = responder(function(stats) {
if(!stats.isDirectory())
this.emit('error', 'Not a repo');
else
stat(this.objectsPath).
on('data', this.objectDirOkay()).
on('error', this.emit.bind(this, 'error'));
});
RepoPathValidator.prototype.objectDirOkay = responder(function(stats) {
if(!stats.isDirectory())
this.emit('error', 'Not a repo');
else
readFile(this.indexFilePath).
on('data', this.indexFileOkay()).
on('error', this.emit.bind(this, 'error'));
});
RepoPathValidator.prototype.indexFileOkay = responder(function(data) {
this.indexData = data;
readFile(this.headFilePath).
on('data', this.headFileOkay()).
on('error', this.emit.bind(this, 'error'));
});
RepoPathValidator.prototype.headFileOkay = responder(function(data) {
this.headData = data;
this.emit('data', this);
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment