从中间件获取一个值,以便在Node.js的另一个模块的函数中使用它

ep6jt1vc  于 2023-06-29  发布在  Node.js
关注(0)|答案(1)|浏览(87)

我在authenticateUser.js中创建了authenticateUser中间件,

async function authenticateUser(req, res, next) {
  const authHeader = req.headers.authorization;
  if (!authHeader) {
    return res.status(401).json({ message: 'Unauthorized access!' });

  }

  try {
    const accessToken = await authHeader.split(' ')[1];
    // Check if the user exists and has the same access token
// Verify the JWT access token and extract the payload
const payload = jwt.verify(accessToken, process.env.ACCESS_TOKEN_SECRET);
   // const role = payload.role;
   const {email,uid, role} = payload;

   
    const user = await UserClient.findOne({ email });
    if (!user || user.accessToken !== accessToken) {
      return res.status(401).json({ message: 'Unauthorized access!' });
    }
 

    // expose the user role , client Id from the payload object for further processing
    req.role = role;
    req.email = email;
    req.uid = uid;

    // Call the next middleware to continue with the request processing
    next();
  } catch (error) {
    return res.status(401).json({ message: 'Unauthorized access!' });
  }
}

在这里,当我需要在另一个路由器中使用email值时,比如说router.get("/user",authenticateUser,async(req,res)=>{}),我可以使用const email= req.email; console.log(email)在users.js模块中使用email值。但我的问题是,当我需要在函数中使用此email值时,我该如何做?
我需要使用email值的函数如下(在sites.js文件中);

async function addSitesToUser() {
      try {
<-------Need to use email value here-------->
        const userData = await UserClient.findOne({email});
    
        if(!userData.siteList || userData.siteList.length === 0){
          const updatedSites = await UserClient.findOneAndUpdate(
            { email },
            { $push: { siteList: { $each: sites } } },
            { upsert: true,new: true }
          );
        } else{
          const existingSiteIds = userData.siteList.map(site => site.siteId);
          // console.log("**exist: "+existingSiteIds)
          const newSites = sites.filter(site => !existingSiteIds.includes(site.siteId));
          // console.log("**newsit: "+newSites)
          userData.siteList.push(...newSites);
          await userData.save();
        }
      } catch (error) {
        console.error('Error adding sites');
      }
    }

我从index.js await addSitesToUser();调用了上面的函数

g2ieeal7

g2ieeal71#

您可以只将电子邮件作为输入传递给函数

router.get("/user",authenticateUser,async(req,res)=>{
    await addSitesToUser(req.email)
})

但是有一个更好的方法来处理这个IMO。在对请求进行身份验证时,您已经获取了用户一次。只需在请求中设置整个用户对象,这样就不必在特定请求的生命周期中的任何地方获取它。因此,在中间件中,只需

req.user = user

然后将req对象向下传递给函数,这样您就可以从任何函数访问用户

router.get("/user", authenticateUser, async (req, res) => {
  await addSitesToUser(req);
  // function body
});

和addSitesToUser函数内部的

async function addSitesToUser(req) {
      try {
        const userData = req.user;

        // do whatever you want to do
      } catch (error) {
        console.error('Error adding sites');
      }
    }

相关问题