Node.js+MongoDB登录脚本无法匹配已注册用户数据求助
问题:登录功能无法正常生效
用Node.js编写了注册与登录脚本,将用户数据存储至MongoDB,预期已注册用户可通过注册邮箱登录,但当前登录功能无法正常生效。这是首次为React应用对接后端,以下是后端及React前端代码,请求排查修复:
后端代码
const User = require("./models/user"); const Worker = require("./models/worker"); app.post("/register", async (req, res) => { try { const { username, email, password } = req.body; // 检查邮箱是否已注册 const existingUser = await User.findOne({ email }); if (existingUser) { console.log("Email already registered:", email); // 调试日志 return res.status(400).json({ message: "Email already registered" }); } // 创建新用户 const newUser = new User({ username, email, password }); // 生成并存储验证令牌 newUser.verificationToken = crypto.randomBytes(20).toString("hex"); // 保存用户到数据库 await newUser.save(); // 调试日志验证数据 console.log("New User Registered:", newUser); // 发送验证邮件 // 使用你偏好的邮件服务或库发送邮件 sendVerificationEmail(newUser.email, newUser.verificationToken); res.status(201).json({ message: "Registration successful. Please check your email for verification.", }); } catch (error) { console.log("Error during registration:", error); // 调试日志 res.status(500).json({ message: "Registration failed" }); } }); const generateSecretKey = () => { const secretKey = crypto.randomBytes(32).toString("hex"); return secretKey; }; const secretKey = generateSecretKey(); // 用户登录接口 app.post("/login", async (req, res) => { try { const { email, password } = req.body; // 检查用户是否存在 const user = await User.findOne({ email }); if (!user) { return res.status(401).json({ message: "Invalid email or password" }); } // 检查密码是否正确 if (user.password !== password) { return res.status(401).json({ message: "Invalid password" }); } // 生成token const token = jwt.sign({ userId: user._id }, secretKey); res.status(200).json({ token }); } catch (error) { res.status(500).json({ message: "Login Failed" }); } });
前端代码
const handleLogin = async () => { // 构造登录请求参数 const user = { email: email, password: password, }; try { const response = await fetch("http://10.0.2.2:3000/login", { method: "POST", headers: { "Content-Type": "application/json", }, body: JSON.stringify(user), }); if (response.ok) { Alert.alert("Success Login"); navigation.navigate("Home"); // 登录成功后跳转到首页 } else { setButtonBgColor("#FF0000"); Alert.alert("Login Error", "Invalid Email or Password"); } } catch (error) { console.error(error); // 处理网络或其他错误 } };
排查修复方案
1. 解决跨域问题
前端与后端域名/端口不同会触发跨域拦截,导致请求失败:
- 安装cors依赖:
npm install cors - 在后端代码开头引入并启用:
const cors = require('cors'); app.use(cors());
2. 修复密码存储与验证逻辑(核心功能+安全性)
当前明文存储密码,不仅不安全,还可能因编码/特殊字符导致比对失败,改用bcrypt加密:
- 安装bcrypt:
npm install bcrypt - 修改注册代码的密码处理:
const bcrypt = require('bcrypt'); // 注册逻辑中,创建用户前添加: const saltRounds = 10; const hashedPassword = await bcrypt.hash(password, saltRounds); const newUser = new User({ username, email, password: hashedPassword });
- 修改登录代码的密码比对:
// 替换原有的`if (user.password !== password)` const isPasswordValid = await bcrypt.compare(password, user.password); if (!isPasswordValid) { return res.status(401).json({ message: "Invalid password" }); }
3. 修复JWT密钥持久化问题
当前每次重启服务都会生成新的secretKey,导致之前的token失效,改用环境变量存储:
- 安装dotenv:
npm install dotenv - 创建
.env文件,添加:SECRET_KEY=你的32位随机密钥(可使用之前generateSecretKey生成的字符串) - 在后端代码中引入:
require('dotenv').config(); const secretKey = process.env.SECRET_KEY;
4. 检查User模型定义
确保models/user.js中包含password字段,否则注册时不会存储密码:
const mongoose = require('mongoose'); const userSchema = new mongoose.Schema({ username: { type: String, required: true }, email: { type: String, required: true, unique: true }, password: { type: String, required: true }, verificationToken: String, isVerified: { type: Boolean, default: false } // 可选,用于邮箱验证逻辑 }); module.exports = mongoose.model('User', userSchema);
5. 前端调试优化
添加更详细的错误反馈,帮助定位问题:
catch (error) { console.error("登录请求异常详情:", error); Alert.alert("登录失败", "网络请求错误,请检查后端服务是否启动或配置正确"); }
同时打开调试工具的Network面板,查看请求的状态码和响应内容,精准定位问题。
内容的提问来源于stack exchange,提问作者Crdnpyaad
相关产品推荐
相关产品推荐

