You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

72 lines
1.8 KiB
JavaScript

var url = require('url');
var NotFoundError = require('./error').NotFound;
var RouteNode = require('./route-node');
var utils = require('./utils');
var assign = utils.assign;
var isArray = utils.isArray;
var isFunction = utils.isFunction;
var isString = utils.isString;
var noop = utils.noop;
function Router() {
this.routes = new RouteNode();
}
assign(Router.prototype, {
add: function add(path, handler) {
return this.routes.add(this._uriToParts(path), handler);
},
route: function route(path, options, done) {
if (done == null && isFunction(options)) {
done = options;
options = {};
}
options = options || {};
var routeArray = this._uriToParts(path);
done = done || noop;
function _routeCallback(err, func, context, args) {
if (err) {
return done(err);
} else {
if (isFunction(func)) {
return done(null, func.apply(context, args));
} else {
return done(new NotFoundError('not found', {location: path}));
}
}
}
return this.routes.get(routeArray, (options.args || []), _routeCallback);
},
_uriToParts: function _uriToParts(uri) {
if (isString(uri)) {
return url.parse(uri)
.pathname
.split('/')
.filter(function (str) { return str !== ''; });
} else if (isArray(uri)) {
return uri.reduce(this._uriToPartsReducer.bind(this), []);
}
},
_uriToPartsReducer: function _uriToPartsReducer(memo, item) {
if (isArray(item)) {
return memo.concat(item);
} else if (isString(item)) {
return memo.concat(this._uriToParts(item));
} else {
return memo.concat(item);
}
}
});
Router.isNotFound = function isNotFound(err) {
return err instanceof NotFoundError;
};
module.exports = Router;