使用Passport实现用户注册认证遇MongooseError报错求助
问题:Passport+Mongoose用户认证出现
Query.prototype.exec()回调报错 使用Passport实现用户注册与认证功能,注册表单可正常运行,但触发会话反序列化时出现如下MongooseError:
throw new MongooseError('Query.prototype.exec() no longer accepts a callback'); ^ MongooseError: Query.prototype.exec() no longer accepts a callback at Function.schema.statics.findByUsername (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\passport-local-mongoose\index.js:298:13) at C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\passport-local-mongoose\index.js:218:12 at pass (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\passport\lib\authenticator.js:354:9) at Authenticator.deserializeUser (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\passport\lib\authenticator.js:359:5) at SessionStrategy.authenticate (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\passport\lib\strategies\session.js:61:10) at attempt (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\passport\lib\middleware\authenticate.js:369:16) at authenticate (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\passport\lib\middleware\authenticate.js:370:7) at Layer.handle [as handle_request] (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\express\lib\router\layer.js:95:5) at trim_prefix (C:\Users\ANKUSH\OneDrive\Desktop\project_IWT\node_modules\express\lib\router\index.js:328:13)
相关实现代码
//jshint esversion:6 const express = require("express"); const bodyparser = require("body-parser"); const ejs = require("ejs"); const mongoose = require("mongoose"); const bcrypt = require("bcrypt"); const session = require("express-session"); const passport = require("passport"); const passportLocalMongoose = require("passport-local-mongoose"); const app = express(); app.use(express.static("public")); app.set('view engine', 'ejs'); app.use(bodyparser.urlencoded({ extended: true })); app.use(session({ secret:"Our Little Secret", resave:false, saveUninitialized: false })); app.use(passport.initialize()); app.use(passport.session()); mongoose.connect('mongodb://0.0.0.0:27017/iwtDB', { useNewUrlParser: true }); mongoose.set("strictQuery", true); const UserSchema = new mongoose.Schema({ username:String, ids:String, password:String, email:String, age:String, gender:String, address:String, branch:String, skill:String }); UserSchema.plugin(passportLocalMongoose); const User = new mongoose.model("user", UserSchema); passport.use(User.createStrategy()); passport.serializeUser(User.serializeUser()); passport.deserializeUser(User.deserializeUser()); app.get("/", function (req, res) { res.render("main"); }); app.get("/login", function (req, res) { res.render("login", { wrongEmail: "", wrongPassword: "" }); }); app.get("/form", function (req, res) { res.render("form"); }); app.get("/main",function(req,res){ if(req.isAuthenticated()) { res.render("main"); } else { res.redirect("/login"); } }); app.get("/logout",function(req,res){ req.logout(function(err){res.redirect("/")}); }); app.post("/form", function (req, res) { User.register({ username:req.body.username, ids:req.body.ids, email:req.body.email, age:req.body.age, gender:req.body.gender, address:req.body.gender, branch:req.body.branch, skill:req.body.skill },req.body.password,function(err,user){ if(err){ console.log(err); res.redirect("/form"); } else { passport.authenticate("local")(req,res,function(){ res.redirect("/main"); }); } }); }); app.post("/login", function (req, res) { const user = new User({ username:req.body.username, name:req.body.name, password:req.body.password }); req.login(user, function(err){ if(err) { console.log(err); } else { passport.authenticate("local")(req,res,function(){ res.redirect("/secrets"); }); } }); }); app.listen(3000, function () { console.log("Server started on port 3000"); });
解决方案
- 核心原因:
passport-local-mongoose版本过低,与Mongoose 6.x+版本不兼容。新版Mongoose已移除Query.prototype.exec()的回调参数支持,而旧版passport-local-mongoose仍在使用该写法。 - 解决步骤:
- 升级
passport-local-mongoose到最新兼容版本,执行命令:npm update passport-local-mongoose - 修复代码中的冗余与错误:
- 注册路由中
address:req.body.gender是错误赋值,应改为address:req.body.address - 登录路由中
res.redirect("/secrets")指向未定义的路由,应改为res.redirect("/main") - 登录代码中
name:req.body.name属于冗余字段,UserSchema未定义,可删除
- 注册路由中
- 升级
内容的提问来源于stack exchange,提问作者01-CSEC2-3_ANKUSH KUMAR
相关产品推荐
相关产品推荐

