1

I have an app with controllers in several files, like this:

var aRoutes = require('./controllers/controllerA');
var bRoutes = require('./controllers/controllerB');
var cRoutes = require('./controllers/controllerC');

app.use('/a', aRoutes);
app.use('/b', bRoutes);
app.use('/c', cRoutes);
// ... several more

And I have a middleware function like this...

app.use(function (req, res, next) {
    // do a middleware thing
    // but not if route == x or y or z or ... yuck!
});

And I want that middleware to run on everything except the aRoutes. I've seen an answer like this, which suggests adding a check in the middleware fn for every route to be excluded but that's terrible, I think. There might be a lot of routes to check, and it forces me to touch the code in two places when I add one of those exception routes.

There must be a better way, right?

Community
  • 1
  • 1
user1272965
  • 2,814
  • 8
  • 29
  • 49
  • Use separate routers and put the middleware call in the routers you want it in and not in the routers you don't. As long as each router has its own path (which it looks like you do), you'll be set. – jfriend00 May 17 '16 at 02:21

1 Answers1

2

Assuming I understand you correctly you could solve it by rearranging the order of the middleware and routes.

var aRoutes = require('./controllers/controllerA');
var bRoutes = require('./controllers/controllerB');
var cRoutes = require('./controllers/controllerC');

app.use('/a', aRoutes);

app.use('/',function (req, res, next) {
    // do a middleware thing
    next();
});

app.use('/b', bRoutes);
app.use('/c', cRoutes);
// ... several more

Now, if you end your aRoutes with a res.render or some other action that ends the request-response cycle and not with a next(), the middleware will never run on the aRoutes.

It will however run on all the other routes. This of course only works if you want the middleware to start the request-response cycle. If you want it somewhere else you have to rearrange the code accordingly.

tomtom
  • 642
  • 7
  • 12