繁体   English   中英

如何在节点应用程序中将存储在 redis 数据库中的 jwt 刷新令牌列入黑名单?

[英]How do I blacklist a jwt refresh token stored in redis database in a node application?

我正在使用节点 mongodb 和 reactjs 构建博客应用程序。 我有 jwt 系统工作,当用户登录时,用户同时生成 accessToken 和 refresh_Token。 refresh_Token 存储在 redis 数据库中。 refresh_Token 持续 30 天,而 accessToken 持续 15 分钟。 我创建了一个路由,一旦 accessToken 在 15 分钟内过期,就会生成新的 refresh_Token 和 accessToken。 但是,我一直在网上搜索如何在每次生成新的 acceesToken 和 refresh_Token 时将我存储在 redis 数据库中的先前生成的 refresh_Token 列入黑名单。 任何人都可以帮助我编写正确的代码以使其正常工作吗? 我想在注销时实施黑名单,并且每次重新生成新的 accessToken 和 refresh_Tokens 集。 到目前为止,这是我的代码:

//login

const login = async (req, res) =>{
 try {
    const user = await User.findOne({username: req.body.username})
    let passValidate
    if(user) {
        passValidate = await bcrypt.compare(req.body.password, user.password)
    }

    if(!user || !passValidate || user.role === "admin") {
        res.status(400).json("Wrong credentials");
    } else {
        const {password, ...others} = user._doc;

        //generate access token
        const token = jwt.sign({userId: user._id, username:user.username, role: user.role}, process.env.JWT_SECRET, {
            expiresIn: process.env.JWT_LIFETIME});

        //generate refresh token
         const refresh_Token = jwt.sign({userId: user._id, username:user.username, role: user.role}, process.env.Refresh_Secret);
         //check refreshtoken in redis database

         await client.get(user._id.toString(), (err, data)=>{
            if(err) throw err;

        //set refresh token in redis database
            client.set(user._id.toString(), JSON.stringify(refresh_Token));
         }); 
        res.status(200).json({user: {username: user.username, userId: user._id}, token, refresh_Token})
    } 
} catch(err) {
    res.status(500).json(err);
}
}

验证访问令牌的代码:

const jwt = require("jsonwebtoken")

 const verify = (req, res, next) =>{
 const authHeader = req.headers.authorization;
 if(authHeader){
    const token = authHeader.split(" ")[1];

    jwt.verify(token, process.env.JWT_SECRET, (err, user)=>{
        if(err){
            return res.status(403).json("Token is not valid");
        }
        req.user = user;
        next();
    });
} else{
    res.status(401).json("You're not authenticated")
}
}

module.exports = 验证

登录路径:

const {login} = require('../controller/auth');
router.post('/login', login);

验证 refresh_Token 的代码

const redis_client = require('../reditConnect');

const refreshTokenverify = async (req, res, next) =>{
//check for the header

const authHeader = req.headers.authorization;
if(!authHeader || !authHeader.startsWith('bearer')){
   return res.status(401).json({message: "Your session is not valid"})
};

const token = authHeader.split(' ')[1];

try{
const payload = jwt.verify(token, process.env.Refresh_Secret)
//attach the user to the job routes
req.user = {userId:payload.userId};

  await redis_client.get(payload.userId.toString(), (err, data)=>{
        if(err){
            console.log(err)
        };
        if(data === null) return res.status(401).json({message: "Token not found in  database"});
        if(JSON.parse(data).refresh_Token != token) return res.status(401).json({message:  "Invaid request"});
 })

 next()
}catch(err){
    console.log(err)
    return res.status(401).json({message: "Invalid token"})
    
}
};

每次访问令牌每 15 分钟过期时重新生成新的 accessToken 和 refresh_Token 的代码:

const regenrateToken = async (req, res)=>{
const userId = req.user.userId


 const token = jwt.sign({userId: req.user.userId, username:req.user.username, role:  req.user.role}, process.env.JWT_SECRET, {
 expiresIn: process.env.JWT_LIFETIME});

 refresh_Token = jwt.sign({userId: req.user.userId}, process.env.Refresh_Secret);

await redis_client.set(req.user.userId.toString(), JSON.stringify(refresh_Token))
 res.status(401).json({data: {token, refresh_Token}});

 return refresh_Token
 //console.log(req)
  
};

Refresh_Token 路由:

const {refreshTokenverify, regenrateToken} = require('../middleware/refreshTokenVerify');

router.post('/refresh', refreshTokenverify, regenrateToken);

我还没有写注销代码。 我希望排序能够将以前使用的 refresh_Tokens 列入黑名单,因为它们的有效期为 30 天。 那么,我该怎么做呢?

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM