【问题标题】:Unexpected behavior in JWT authentication using cookies使用 cookie 的 JWT 身份验证中的意外行为
【发布时间】:2020-12-21 22:26:04
【问题描述】:

我正在学习 Node.js 并制作我的第一个项目。我正在使用 JWT 对项目进行用户身份验证。我正在使用 cookie 发送 JWT,并且在服务器端我能够提取 cookie 并正确获取预期的有效负载。但是,我在身份验证功能中遇到了意外行为,我总是被一个特定用户注册。

登录路径:

usersRouter.route('/login')
.post(passport.authenticate('local'), (req,res) => {
  console.log('Generating token for: ', req.user._id);
  var token = authenticate.getToken({_id: req.user._id});

  res.statusCode = 200;
  res.cookie('jwt', token, {signed: true});
  res.redirect('/');
  
})

验证码:

exports.getToken = function(user){
    return jwt.sign(user, config.secretKey, {
        expiresIn: 3600
    });
};

var extractFromCookie = function (req)
{   
    var token = null;
    if(req && req.signedCookies)
        token = req.signedCookies.jwt;
    return token;
}

var opts = {};
opts.jwtFromRequest = extractFromCookie;
opts.secretOrKey = config.secretKey;

exports.jwtPassport = passport.use(new JwtStrategy(opts, (jwt_payload, done) => {
    console.log("Jwt Payload: ", jwt_payload);

    User.findOne({id: jwt_payload.sub}, (err,user) => {
        if(err){
            return done(err,false);
        }
        else if(user){
            console.log('Found user is: ', user);
            return done(null, user);
        }
        else
            return done(null,false);
    });
}));


exports.verifyUser = passport.authenticate('jwt', {session:false});

在控制台打印

Jwt Payload:  { _id: '5f49430180e4092eac7962be', iat: 1599066593, exp: 1599070193 }
Found user is: 
{
  _id: 5f4904d106efe130084808a4,
   .
   .
   . other details
   .
}

搜索是如何产生具有不同 id 的用户的?我无法弄清楚为什么会这样。请帮忙!

编辑: getToken 是一个从登录路由器发送的用户 id 生成令牌的函数。

【问题讨论】:

  • authenticate.getToken 是什么?
  • @WiktorZychla getToken 是一个使用用户 id 生成令牌的函数。我已经编辑了帖子。

标签: node.js mongoose jwt passport.js passport-local


【解决方案1】:

您不小心访问了jwt_payload 中的未定义属性sub,因此您实际上将undefined 作为值发送给findOne 函数。

这应该可行。

User.findById(jwt_payload._id, (err,user) => {

【讨论】:

  • 我曾尝试过这样做,但当时甚至没有执行 User.findOne 函数。它只是发送未经授权的用户。
  • findOne 回调是否被调用? err/user的值是多少?
  • findOne 回调被调用,但由于无法找到“id”字段而出现错误(状态 401)。
【解决方案2】:

毕竟只是一些小错误。

唯一需要改变的是: User.findOne({id: jwt_payload.sub}, (err,user) =>

正如@Michael 指出的,jwt_payload 中没有字段名称 sub,我们需要用 _id 代替。此外,在 User 模式中,它是 _id 字段而不是 id 字段。

做出这些改变,中提琴!

【讨论】:

  • 我编辑了我的答案,我认为这是正确的答案:)
猜你喜欢
  • 2018-12-14
  • 2020-12-19
  • 2016-03-21
  • 2015-09-13
  • 2018-09-02
  • 2021-12-24
  • 1970-01-01
  • 1970-01-01
  • 2016-04-07
相关资源
最近更新 更多