90

如何结合本地护照以在成功认证时返回 JWT 令牌?

我想使用node-jwt-simple并查看passport.js我不知道该怎么做。

var passport = require('passport')
  , LocalStrategy = require('passport-local').Strategy;

passport.use(new LocalStrategy(
  function(username, password, done) {
    User.findOne({ username: username }, function(err, user) {
      if (err) { return done(err); }
      if (!user) {
        return done(null, false, { message: 'Incorrect username.' });
      }
      if (!user.validPassword(password)) {
        return done(null, false, { message: 'Incorrect password.' });
      }
      return done(null, user);
    });
  }
));

调用 done() 时是否可以返回令牌?像这样的东西......(只是伪代码)

if(User.validCredentials(username, password)) {
  var token = jwt.encode({username: username}, tokenSecret);
  done(null, {token : token}); //is this possible?
}

如果没有,我该如何退回令牌?

4

3 回答 3

126

我想到了!

首先,您需要实施正确的策略。在我的例子中是 LocalStrategy,你需要提供你的验证逻辑。例如,让我们使用本地护照中的那个。

var passport = require('passport')
  , LocalStrategy = require('passport-local').Strategy;

passport.use(new LocalStrategy(
  function(username, password, done) {
    User.findOne({ username: username }, function(err, user) {
      if (err) { return done(err); }
      if (!user) {
        return done(null, false, { message: 'Incorrect username.' });
      }
      if (!user.validPassword(password)) {
        return done(null, false, { message: 'Incorrect password.' });
      }
      return done(null, user);
    });
  }
));

您提供的验证回调function(username, password, done)将负责查找您的用户并检查密码是否匹配(超出问题和我的答案的范围)

passport.js 期望它能够工作的几个部分,一个是你在策略中返回用户。我试图改变那部分代码,这是错误的。回调期望false验证是否失败,object如果您成功则返回一个(经过验证的用户)。

现在....如何集成 JWT?

在您的登录路线中,您将不得不处理成功的身份验证或不成功的身份验证。在这里,您需要添加 JWT 令牌创建。像这样:

(请记住禁用会话,否则您将必须实现序列化和反序列化功能。如果您不持久化会话,则不需要这些功能,如果您使用基于令牌的身份验证,则不需要)

来自本地护照示例:(添加了 JWT 令牌)

// POST /login
//   This is an alternative implementation that uses a custom callback to
//   achieve the same functionality.
app.post('/login', function(req, res, next) {
  passport.authenticate('local', function(err, user, info) {
    if (err) { return next(err) }
    if (!user) {
      return res.json(401, { error: 'message' });
    }

    //user has authenticated correctly thus we create a JWT token 
    var token = jwt.encode({ username: 'somedata'}, tokenSecret);
    res.json({ token : token });

  })(req, res, next);
});

就是这样!现在,当您调用 /login 并 POST 用户名和密码(应始终通过 SSL)时,上面的第一个代码片段将尝试根据您提供的用户名查找用户,然后检查密码是否匹配(当然您需要改变它以满足您的需要)。

之后,您的登录路线将被调用,您可以在此处处理返回错误或有效令牌。

希望这会对某人有所帮助。如果我犯了任何错误或忘记了什么,请告诉我。

于 2013-11-28T21:02:47.043 回答
19

这是一个很好的解决方案,我只想添加这个:

var expressJwt = require('express-jwt');

app.use('/api', expressJwt({secret: secret}));

我喜欢使用“express-jwt”来验证令牌。

顺便说一句:这篇文章非常适合学习如何使用 Angular 在客户端处理令牌,以便在每个请求中将其发送回

https://auth0.com/blog/2014/01/07/angularjs-authentication-with-cookies-vs-token/

于 2014-08-15T17:19:25.770 回答
4

这是我正在专门使用 api 令牌的样板(没有会话......当然不是那个会话不好;只是我们正在使用令牌方法): https ://github.com/roblevintennis/passport -api-tokens

于 2013-12-14T17:44:12.083 回答