Expressjs:如何共享路由中间件
我定义了多个路由中间件,并希望跨多个路由/控制器共享它们。
这是我的设置:
app.js需要./routes/index.js:
// load fs module var fs = require('fs'); // import routing files module.exports = function(app){ fs.readdirSync(__dirname).forEach(function(file) { if (file == "index.js") return; var name = file.substr(0, file.indexOf('.')); require('./' + name)(app); }); };
index.js在dir中自动加载所有路由。 可能的路线文件可能如下所示:
module.exports = function(app) { app.get('/contacts', function(req, res, next) { // routing stuff }); };
现在我得到了路由中间件:
function isAuthenticated(req, res, next) { if (!req.session.authenticated) return next(new Error('user not authenticated')); }; function loadUser(req, res, next) { var query = User.findById(req.session.user_id); query.populate('contacts'); query.exec(function(err, user) { if (err) return next(err); req.user = user; next(); }); }
我想要使用像:
var User = require('../models/user'); module.exports = function(app) { app.get('/contacts', isAuthenticated, loadUser, function(req, res, next) { res.json(req.user.contacts); }); };
我也想避免要求他们跨所有路由文件。
一个可能的解决scheme也将是:
// load fs module var fs = require('fs'); var routeMiddleware = { loadUser: function(req, res, next) { // logic }, isAuthenticated: function(req, res, next) { // logic }, }; // import routing files module.exports = function(app){ fs.readdirSync(__dirname).forEach(function(file) { if (file == "index.js") return; var name = file.substr(0, file.indexOf('.')); require('./' + name)(app, routeMiddleware); }); };
但我觉得不是最好的…
我个人会在应用程序中声明共享的中间件,而不是在控制器中,即:
路线/ home.js:
module.exports = function(req, res, next) { \\ Code }
app.js:
app.get('/', thisMiddleware, thatMiddleware, require('./routes/home'))
你也可以创build一个堆栈(数组,而不是对象):
theseMiddlewares = [thisMiddleware, thatMiddleware] app.get('/', theseMiddlewares, require('./routes/home'))
如果这些中间件用于除less数几个之外的所有路由,则可以执行以下操作:
theseMiddlewares = function(req, res, next) { if (req.url.match(some_regex_for_urls_to_skip)) next() else { \\ do stuff... next() } }
现在你可以app.use(theseMiddlewares)
这个中间件,或者如果它需要按照某个相对于其他中间件的顺序发生,你可以使用app.all('*', theseMiddlewares)