PassportJS - 自定义回调并将 Session 设置为 false

Posted

技术标签:

【中文标题】PassportJS - 自定义回调并将 Session 设置为 false【英文标题】:PassportJS - Custom Callback and set Session to false 【发布时间】:2014-09-30 00:41:26 【问题描述】:

是否可以使用自定义回调并禁用会话?在文档中,它显示了如何禁用会话和自定义回调,但我如何组合它们?

app.get('/login', function(req, res, next) 
  passport.authenticate('local', function(err, user, info) 
    if (err)  return next(err); 
    if (!user)  return res.redirect('/login'); 

    req.logIn(user, function(err) 

      // I'm getting an error here
      // [Error: Failed to serialize user into session]

      if (err)  return next(err); 
      return res.redirect('/users/' + user.username);
    );
  )(req, res, next);
);

【问题讨论】:

【参考方案1】:

你试过直接组合它们吗? 类似的东西:

passport.authenticate('local',  "session": false , function(err,user,info)
   //blablabla
);

从护照的源代码中,authenticate 定义如下:

Authenticator.prototype.authenticate = function(strategy, options, callback) 

所以我不明白为什么你不能同时使用这两个参数。

【讨论】:

这是不正确的(至少对于当前的 Passport)。会话参数需要按照@marekozw 的回答与登录方法一起传递。【参考方案2】:

请确保您使用最新版本的passport(今天是0.2.1)。

请尝试将 session: false 作为req.logIn() 函数的第二个参数传递:

app.get('/login', function (req, res, next) 
  passport.authenticate('local', function (err, user, info) 
    if (err)  return next(err); 
    if (!user)  return res.redirect('/login'); 

    req.logIn(user,  session: false , function (err) 

      // Should not cause any errors

      if (err)  return next(err); 
      return res.redirect('/users/' + user.username);
    );
  )(req, res, next);
);

原因:

乍一看,在passport.authenticate() 中传递 session: false 似乎是合理的,因为该方法的源代码如下:

Authenticator.prototype.authenticate = function(strategy, options, callback) 
  return this._framework.authenticate(this, strategy, options, callback);
;

所以它应该能够尊重第二个参数。但是,如果您开始深入了解函数调用堆栈,您会发现options 参数的session 属性被完全忽略了。我的意思是,里面没有提到options.session

this._framework.authenticate(this, strategy, options, callback);

功能。

所以基本上你想在req.logIn() 函数中传递它。该函数源码如下:

req.logIn = function(user, options, done) 
  if (!this._passport) throw new Error('passport.initialize() middleware not in use');

  if (!done && typeof options === 'function') 
    done = options;
    options = ;
  
  options = options || ;
  var property = this._passport.instance._userProperty || 'user';
  var session = (options.session === undefined) ? true : options.session;

  this[property] = user;
  if (session)  // HERE! It will not try to serialize anything if you pass session: false
    var self = this;
    this._passport.instance.serializeUser(user, function(err, obj) 
      if (err)  self[property] = null; return done(err); 
      self._passport.session.user = obj;
      done();
    );
   else 
    done && done();
  

附:请考虑使用npm install [package-name] --save 安装您的npm 依赖项,而不是手动创建package.jsonnpm 会自动获取最新的稳定版本。

【讨论】:

我认为这应该被标记为好的 :) 谢谢@marekozw 目前Passport自动扩展github.com/jaredhanson/passport/blob/master/lib/http/request.js中的http.IncomingMessage原型,'req.login'/'req.logIn'方法由'passport.authenticate()'自动调用passportjs.org/guide/login

以上是关于PassportJS - 自定义回调并将 Session 设置为 false的主要内容,如果未能解决你的问题,请参考以下文章

Prorogate PassportJS 中的自定义错误

Passportjs 成功回调从未被调用

通过回调或猫鼬模型验证 PassportJS?

Express Passportjs在路由器回调中未进行身份验证

在我自己的 Web 应用程序中使用 passportjs 管理单点登录 - 共享登录

无法使用 PassportJS 读取未定义、NestJS 的属性“validateUser”