diff --git a/lib/application.js b/lib/application.js index 310e6dfef21..a9630035934 100644 --- a/lib/application.js +++ b/lib/application.js @@ -254,7 +254,15 @@ app.use = function use(fn) { */ app.route = function route(path) { - return this.router.route(path); + var routeObj = this.router.route(path); + var self = this; + + // TODO: This isn't the cleanest, but it's non-blocking and ensures synchronous call chains to the route object (ex: .get()) have ran before we trigger the event. + setTimeout(function() { + self.emit('route', routeObj); + },0); + + return routeObj; }; /** @@ -477,6 +485,8 @@ methods.forEach(function (method) { var route = this.route(path); route[method].apply(route, slice.call(arguments, 1)); + // The emit call works when placed here for direct METHOD call on the app, but not when using .route() + //this.emit('route', route); return this; }; }); diff --git a/test/app.route.js b/test/app.route.js index 03ae1293685..e09e5c0d7ce 100644 --- a/test/app.route.js +++ b/test/app.route.js @@ -1,5 +1,6 @@ 'use strict' +var assert = require('node:assert') var express = require('../'); var request = require('supertest'); @@ -62,6 +63,26 @@ describe('app.route', function(){ .expect(404, done); }); + it('should emit "route" when a new route is defined', function(done){ + var app = express() + + app.on('route', function(arg){ + var layer = (app.stack || app.router.stack).find(function(i){ + return i.route.path === '/:foo'; + }); + + assert.strictEqual(arg, layer.route); + assert.strictEqual(arg.path, '/:foo'); + assert.strictEqual(arg.methods.get, true); + done(); + }); + + app.route('/:foo') + .get(function(req, res) { + res.send(req.params.foo); + }); + }); + describe('promise support', function () { it('should pass rejected promise value', function (done) { var app = express() diff --git a/test/app.router.js b/test/app.router.js index 6e7be684e55..12dbc107045 100644 --- a/test/app.router.js +++ b/test/app.router.js @@ -59,6 +59,25 @@ describe('app.router', function () { var app = express(); assert.throws(app[method].bind(app, '/', 3), /argument handler must be a function/); }) + + it('should emit "route" when a new route is defined using ' + method.toUpperCase(), function(done){ + var app = express() + + app.on('route', function(arg){ + var layer = (app.stack || app.router.stack).find(function(i){ + return i.route.path === '/:foo'; + }); + + assert.strictEqual(arg, layer.route); + assert.strictEqual(arg.path, '/:foo'); + assert.strictEqual(arg.methods[method], true); + done(); + }); + + app[method]('/:foo', function(req, res) { + res.send(req.params.foo); + }); + }); }); it('should re-route when method is altered', function (done) {