index.js | |
---|---|
/*
* index.js: Top level module include for utils module.
*
* (C) 2010, Nodejitsu Inc.
*
*/
var sys = require('sys'),
fs = require('fs'),
path = require('path'),
async = require('async'),
colors = require('colors'),
http = require('http'),
eyes = require('eyes'),
mkdirp = require('mkdirp').mkdirp,
spawn = require('child_process').spawn,
haibu = require('haibu');
var utils = exports; | |
Include ExportsExport additional utils components | var base64 = utils.base64 = require('./base64');
var bin = utils.bin = require('./bin'); |
function showWelcome (mode, ipAddress, port)@mode {string} The mode that haibu is currently running in.@ipAddress {string} The IP Address / host that haibu is binding to.@port {int} The port that haibu is binding to.Prints the signature | utils.showWelcome = function (role, ipAddress, port) {
var msg = [
'haibu'.yellow.bold,
'started @'.grey,
ipAddress.green.bold,
'on port'.grey,
port.toString().green.bold,
'as'.grey,
role.green.bold
].join(' ');
sys.puts(' _ _ _ '.yellow);
sys.puts(' | | (_) | | '.yellow);
sys.puts(' | |__ _____ _ | |__ _ _ '.yellow);
sys.puts(' | _ \\ (____ | | | | _ \\ | | | |'.yellow);
sys.puts(' | | | | / ___ | | | | |_) ) | |_| |'.yellow);
sys.puts(' |_| |_| \\_____| |_| |____/ |____/ '.yellow);
sys.puts(' © 2010 Nodejitsu Inc.'.grey);
sys.puts(' All Rights Reserved - www.nodejitsu.com'.grey);
sys.puts(' ' + msg);
}; |
function getIpAddress (callback)@callback {function} The callback function to respond when completeGets the IP Address bound to on the default device on this machine. Will
respect if the device is | utils.getIpAddress = function (callback) {
var ipcheck, address, done = false;
if (process.platform !== 'darwin') { |
If we aren't on Mac OS X | ipcheck = spawn('hostname', ['-i']);
}
else { |
If we are on Mac OS X | ipcheck = spawn('ipconfig', ['getifaddr', 'en1']);
}
|
Get the data from the IP address child process. | ipcheck.stdout.on('data', function (data) {
address = data.toString().trim();
var matches = address.match(/\d+\.\d+\.\d+\.\d+/);
if (typeof matches === 'undefined' || matches.length <= 0) {
if (!done) {
done = true;
callback(new Error('Output was not a valid ip address'));
}
}
});
ipcheck.stderr.on('data', function (data) {
if (!done) {
done = true;
callback(new Error('Error: ' + data.toString()));
}
});
ipcheck.on('exit', function (code) {
if (!done) {
callback(null, address);
}
});
}; |
function createServer (router, logger, secure, port)@contentTypes {Object} Content types for this server to handle.@secure {bool} A value indicating whether this server is sercure[@port] {int} The optional port for this server to listen on.TODO (indexzero): Remove the @secure parameter or use it to indicate HTTPS Creates an instance of http.Server that will log using Winston and route using Journey. | utils.createServer = function (contentTypes, secure, port) {
var server = http.createServer(function (req, res) {
var router, contentType, contentLength, body = '', length = 0, raw;
try {
contentLength = parseInt(req.headers['content-length'], 10);
if (contentLength && contentLength > 0 && !isNaN(contentLength)) {
raw = new Buffer(contentLength);
}
}
catch (ex) { |
Ignore errors. | } |
Append the chunk to body | req.addListener('data', function (chunk) {
body += chunk;
if (contentLength && contentLength > 0 && !isNaN(contentLength)) {
chunk.copy(raw, length, 0);
length += chunk.length;
}
});
req.addListener('end', function () {
if (!req.headers['content-type']) {
req.headers['content-type'] = 'application/json';
}
contentType = req.headers['content-type'] && req.headers['content-type'].match(/([\d|\w|\-]+\/[\d|\w|\-]+)/)[1];
router = contentTypes[contentType];
if (!router || !router.handle) {
res.writeHead(500, { 'Content-Type': 'application/json' });
return res.end(JSON.stringify({ message: 'Unexpected Content-Type: ' + contentType }));
}
if (contentType === 'application/octet-stream') {
if (typeof contentLength === 'undefined' || isNaN(contentLength)) {
res.writeHead(400, { 'Content-Type': 'application/json' });
return res.end(JSON.stringify({ message: 'Content-Length is required' }));
}
body = raw;
} |
Dispatch the request to the router | var logger = router.handle(req, body, function (result) {
res.writeHead(result.status, result.headers);
res.end(result.body.toString());
});
logger.once('log', function (data) {
delete data.date;
haibu.emit('service:incoming', 'info', data);
});
});
});
if (port) {
server.listen(port);
}
return server;
}; |
function randomString (bits)@bits {integer} The number of bits for the random base64 string returned to containrandomString returns a pseude-random ASCII string which contains at least the specified number of bits of entropy the return value is a string of length ⌈bits/6⌉ of characters from the base64 alphabet | var randomString = exports.randomString = function (bits) {
var chars, rand, i, ret;
chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_-';
ret = '';
|
in v8, Math.random() yields 32 pseudo-random bits (in spidermonkey it gives 53) | while (bits > 0) { |
32-bit integer | rand = Math.floor(Math.random() * 0x100000000); |
base 64 means 6 bits per character, so we use the top 30 bits from rand to give 30/6=5 characters. | for (i = 26; i > 0 && bits > 0; i -= 6, bits -= 6) {
ret += chars[0x3F & rand >>> i];
}
}
return ret;
}; |
function getEndKey (startKey)@startKey {string} Startkey paramater for querying CouchDB.Returns the 'endkey' associated with the e.g. | var getEndKey = exports.getEndKey = function (startKey) {
var length = startKey.length;
return startKey.slice(0, length - 1) + String.fromCharCode(startKey.charCodeAt(length - 1) + 1);
}; |
function mixin (target [source0, source1, ...])Copies enumerable properties from | utils.mixin = function (target) {
var objs = Array.prototype.slice.call(arguments, 1);
objs.forEach(function(o) {
Object.keys(o).forEach(function (attr) {
if (! o.__lookupGetter__(attr)) {
target[attr] = o[attr];
}
});
});
return target;
}; |
function clone (object)@object {Object} Object to cloneShallow clones the specified object. | utils.clone = function (object) {
return Object.keys(object).reduce(function (obj, k) {
obj[k] = object[k];
return obj;
}, {});
}; |
function initDirectories (directories, callback)@directories {Object} Optional Directories to initialize@callback {function} Continuation to respond to when completeCreates all of the specified | utils.initDirectories = function (directories, callback) {
if (!callback) {
callback = directories;
directories = null;
}
var paths = [];
directories = directories || haibu.config.get('directories');
Object.keys(directories).forEach(function (key) {
paths.push(directories[key]);
});
function createDir(dir, next) {
mkdirp(dir, 0755, function () {
next();
});
}
async.forEach(paths, createDir, function () {
callback(null, paths);
});
}; |
function cleanDirectories (directories, callback)@directories {Object} Optional Directories to clean@callback {function} Continuation to respond to when completeCleans all of the specified | utils.cleanDirectories = function (directories, callback) {
if (!callback) {
callback = directories;
directories = null;
}
var paths = [];
directories = directories || haibu.config.get('directories');
Object.keys(directories).forEach(function (key) {
paths.push(directories[key]);
});
function removeDir (dir, next) {
exec('rm -rf ' + dir, function (err, stdout, stderr) {
next();
});
}
async.forEach(paths, removeDir, function () {
callback(null, paths);
});
};
|