AndreaNotes1's picture
Upload 36 files
6e13570 verified
Raw History Blame Contribute Delete
1.54 kB
const { verifyAccessToken } = require("../utils/jwt");
const User = require("../models/User");
/**
* Requires a valid, non-expired access token in the Authorization header.
* Attaches the full (fresh) user document to req.user so downstream
* handlers always see current role/lock/tokenVersion state rather than
* trusting stale claims baked into the JWT.
*/
async function requireAuth(req, res, next) {
try {
const header = req.headers.authorization || "";
const [scheme, token] = header.split(" ");
if (scheme !== "Bearer" || !token) {
return res.status(401).json({ error: "Authentication required." });
}
const payload = verifyAccessToken(token);
const user = await User.findById(payload.sub);
if (!user || !user.isActive) {
return res.status(401).json({ error: "Account not found or disabled." });
}
if (user.tokenVersion !== payload.tokenVersion) {
// Token was issued before a password change / forced logout.
return res.status(401).json({ error: "Session expired, please log in again." });
}
req.user = user;
next();
} catch (err) {
return res.status(401).json({ error: "Invalid or expired token." });
}
}
function requireRole(...roles) {
return (req, res, next) => {
if (!req.user || !roles.includes(req.user.role)) {
return res.status(403).json({ error: "You do not have permission to perform this action." });
}
next();
};
}
module.exports = { requireAuth, requireRole };