Express.js中Passport配置文件外导出Discord OAuth2认证中间件失败
解决Discord OAuth2应用中isAuthenticated中间件导出失败的问题
可能的原因及对应解决方案
1. 确保中间件先定义再导出
如果isAuthenticated在导出语句之后才定义,其他文件导入时会拿到undefined。必须把中间件定义放在导出操作之前。
错误示例(index.js):
// 先导出,此时isAuthenticated尚未定义 module.exports = { isAuthenticated }; // 后续才定义中间件 function isAuthenticated(req, res, next) { if (req.isAuthenticated()) return next(); res.redirect('/login'); }
修正后的index.js:
// 先定义中间件逻辑 function isAuthenticated(req, res, next) { if (req.isAuthenticated()) return next(); res.redirect('/login'); } // 再执行导出 module.exports = { isAuthenticated };
2. 检查导出与导入的语法匹配度
确认导出方式和导入方式一致,避免拼写错误或路径错误。
正确导出方式(二选一):
// 方式1:直接挂载到module.exports module.exports.isAuthenticated = function(req, res, next) { if (req.isAuthenticated()) return next(); res.redirect('/login'); }; // 方式2:先定义再赋值 const isAuthenticated = (req, res, next) => { if (req.isAuthenticated()) return next(); res.redirect('/login'); }; exports.isAuthenticated = isAuthenticated;
导入时确保路径正确(示例:路由文件在routes目录,index.js在根目录):
// routes/protected.js const { isAuthenticated } = require('../index'); // 正常使用中间件 router.get('/dashboard', isAuthenticated, (req, res) => { res.send('Welcome to your dashboard'); });
3. 避免循环引用问题
如果路由文件被index.js引入(比如app.use('/routes', require('./routes'))),会触发循环引用,导致index.js未完成加载时,导出的isAuthenticated为undefined。
解决方法:将中间件抽离到独立文件
创建middleware/auth.js单独存放认证中间件:
// middleware/auth.js module.exports.isAuthenticated = (req, res, next) => { if (req.isAuthenticated()) return next(); res.redirect('/login'); };
然后在index.js和路由文件中统一导入该文件:
// index.js const { isAuthenticated } = require('./middleware/auth'); // 正常使用中间件 // routes/protected.js const { isAuthenticated } = require('../middleware/auth'); router.get('/dashboard', isAuthenticated, (req, res) => { // 业务逻辑 });
4. 确认Passport初始化顺序正确
虽然你的问题是导出后拿到undefined,但额外检查Passport初始化步骤,确保req.isAuthenticated()能正常工作:
// index.js中Passport初始化顺序 const express = require('express'); const passport = require('passport'); const DiscordStrategy = require('passport-discord').Strategy; const app = express(); // 必须先初始化Passport app.use(passport.initialize()); app.use(passport.session()); // 配置Discord认证策略 passport.use(new DiscordStrategy({ clientID: 'YOUR_CLIENT_ID', clientSecret: 'YOUR_CLIENT_SECRET', callbackURL: '/auth/discord/callback', scope: ['identify', 'guilds'] }, (accessToken, refreshToken, profile, done) => { // 用户逻辑处理 return done(null, profile); })); passport.serializeUser((user, done) => done(null, user)); passport.deserializeUser((obj, done) => done(null, obj)); // 定义并导出中间件 function isAuthenticated(req, res, next) { if (req.isAuthenticated()) return next(); res.redirect('/login'); } module.exports = { isAuthenticated };
内容的提问来源于stack exchange,提问作者jozef
相关产品推荐
相关产品推荐

