← back to AbramsOS
middleware/auth.js
37 lines
const auth = require('../lib/auth');
// Hydrate req.session + req.userId from the cookie
async function loadSessionMiddleware(req, _res, next) {
const sid = req.cookies?.[auth.SESSION_COOKIE] || req.signedCookies?.[auth.SESSION_COOKIE];
if (!sid) { if (process.env.SINGLE_USER_AUTOLOGIN) req.userId = process.env.SINGLE_USER_AUTOLOGIN; return next(); }
const session = await auth.loadSession(sid);
if (!session) { if (process.env.SINGLE_USER_AUTOLOGIN) req.userId = process.env.SINGLE_USER_AUTOLOGIN; return next(); }
req.session = session;
req.userId = session.user_id;
next();
}
// Reject unauthenticated requests; redirect HTML to /signin, JSON gets 401.
// FLEET BASIC-AUTH MODE: when SINGLE_USER_AUTOLOGIN is set, the app is deployed behind
// nginx HTTP Basic Auth (admin/DW2024!) — the door is already guarded, so trust the
// request and act as the single owner instead of showing the app's own email/TOTP login.
function requireAuth(req, res, next) {
if (req.userId) return next();
if (process.env.SINGLE_USER_AUTOLOGIN) { req.userId = process.env.SINGLE_USER_AUTOLOGIN; return next(); }
if (req.accepts('html')) return res.redirect('/signin?next=' + encodeURIComponent(req.originalUrl));
return res.status(401).json({ error: 'unauthenticated' });
}
// Require recent (within 60s) successful TOTP verify
function requireStepUp(req, res, next) {
if (!req.userId) {
if (req.accepts('html')) return res.redirect('/signin?next=' + encodeURIComponent(req.originalUrl));
return res.status(401).json({ error: 'unauthenticated' });
}
if (auth.isStepUpValid(req.session)) return next();
if (req.accepts('html')) return res.redirect('/step-up?next=' + encodeURIComponent(req.originalUrl));
return res.status(403).json({ error: 'step_up_required' });
}
module.exports = { loadSessionMiddleware, requireAuth, requireStepUp };