提交添加产品表单时出现TypeError: Cannot read properties of undefined (reading 'isLoggedIn')错误
这个错误不是认证逻辑本身的问题,而是中间件顺序错误 + 错误处理时未做安全检查导致的,和文件路径存在间接关联。
错误根源
报错信息TypeError: Cannot read properties of undefined (reading 'isLoggedIn')指向req.session为undefined,但你直接访问了它的isLoggedIn属性。
为什么req.session会是undefined?看你的中间件执行顺序:
// 先执行multer处理文件上传 app.use(multer(...).single('image')); // 再执行session中间件 app.use(session(...));
当提交带文件的表单时,如果multer处理出错(比如images文件夹不存在导致无法写入文件、文件读写权限不足等),错误会直接进入最后的错误处理中间件,但此时session中间件还未执行,req.session根本没被初始化,自然是undefined。
同时你的错误处理中间件没有对req.session做存在性检查,直接访问req.session.isLoggedIn,最终触发了应用崩溃。
修复步骤
1. 调整中间件顺序,将session前置
session中间件需要在所有可能触发错误的中间件(比如multer)之前执行,确保即使后续中间件出错,req.session已经被初始化:
app.use(bodyParser.urlencoded({ extended: false })); // 先初始化session app.use( session({ secret: 'my secret', resave: false, saveUninitialized: false, store: store }) ); // 再处理文件上传 app.use( multer({ storage: fileStorage, fileFilter: fileFilter }).single('image') ); app.use(express.static(path.join(__dirname, 'public'))); app.use('/images', express.static(path.join(__dirname, 'images')));
2. 给错误处理中间件添加安全检查
即使调整了顺序,也要避免直接访问可能为undefined的属性,修改错误处理中间件:
app.use((error, req, res, next) => { res.status(500).render('500', { pageTitle: 'Error!', path: '/500', // 先检查req.session是否存在,再取isLoggedIn isAuthenticated: req.session ? req.session.isLoggedIn : false }); });
(如果你的Node版本支持可选链语法,也可以写成req.session?.isLoggedIn || false)
3. 确保images文件夹存在
multer的destination配置为'images',如果项目根目录下没有这个文件夹,multer会在保存文件时抛出错误,直接触发错误处理中间件。你可以手动创建images文件夹,也可以在代码里自动创建:
const fs = require('fs'); const imagesDir = path.join(__dirname, 'images'); if (!fs.existsSync(imagesDir)) { fs.mkdirSync(imagesDir); }
额外验证
你能正常登录说明认证逻辑本身没问题,只是在文件上传出错的场景下,错误处理环节没处理好req.session的边界情况。调整后,即使multer出错,应用也不会崩溃,而是正常渲染500页面。
内容的提问来源于stack exchange,提问作者tukitooo1998

