如何在条件中间件中使用Node.js Express-session?

时间:2015-05-07 20:35:36

标签: node.js session express

var express = require('express')
var parseurl = require('parseurl')
var session = require('express-session')

var app = express()


app.use(session({
  secret: 'keyboard cat',
  resave: false,
  saveUninitialized: true
}))

这是我的简单代码。但是,我想仅在req.url包含/web时才使用会话。有没有办法将它包装在我自己的中间件中?

我试过了:

function setSession(req,res,next){
    if(req.url.indexOf('/api') != 0){
        app.use(session({
            secret: 'keyboard cat',
            resave: false,
            saveUninitialized: true
        }));
        next();
    }else{
        next();
    }
};

然后

app.use(setSession);

但在我的控制器中设置req.session.hello = "world"会产生:TypeError: Cannot set property 'hello' of undefined。简单地说,它不起作用。我的论点在我的中间件中是错误的吗?

1 个答案:

答案 0 :(得分:1)

  

但是,如果req.url包含/ web,我只想使用session。有没有办法将它包装在我自己的中间件中?

你当然可以。您可以使用express.Router创建子路由,如下所示:

var sessionMiddleware = session({
    secret: 'keyboard cat',
    resave: false,
    saveUninitialized: true
});

var webRoutes = express.Router()
    .get('/', function(req, res, next) {
        res.send('I have a session!');
    });

var nonWebRoutes = express.Router()
    .get('/', function(req, res, next) {
        res.send('No session here');
    });


app.use('/web', express.Router()
    .use(sessionMiddleware)
    .use(webRoutes));

app.use('/nonweb', nonWebRoutes);

修改

如果您想要有条件地执行中间件功能,您可以这样做:

app.use(function(req, res, next) {
    if (req.url.indexOf('/api') !== 0) {
        sessionMiddleware(req, res, next);
    } else {
        next();
    }
});

app.get('/api', function(req, res, next) {
    res.send(!!req.session); //false
});

app.get('/web', function(req, res, next) {
    res.send(!!req.session); //true
});

但我更喜欢子路由方法,因为它将路径路径结构映射到层次结构,这使得代码更易于阅读,并且更容易合并使用会话的其他中间件,例如passport.js。