MERN聊天应用用MongoDB Atlas时遇users.findOne()缓冲超时问题
MERN栈聊天应用MongoDB Atlas连接超时问题排查与解决
遇到如下错误:
MongooseError: Operation `users.findOne()` buffering timed out after 10000ms at Timeout.<anonymous> (/Users/thakur/Desktop/web/react_app/chat-app/node_modules/mongoose/lib/drivers/node-mongodb-native/collection.js:185:23) at listOnTimeout (node:internal/timers:569:17) at process.processTimers (node:internal/timers:512:7)
已尝试增加服务器超时时间,但无效果。
相关代码
index.js
const express = require('express'); const dotenv = require('dotenv'); const mongoose = require('mongoose'); const User = require('../Models/userModel'); const userRoutes = require('../Routes/userRoutes'); const app = express(); dotenv.config(); app.use(express.json()); mongoose.set('debug', true); const connectDb = async () => { try { const connect = await mongoose.connect(process.env.MONGO_URL,{ serverSelectionTimeoutMS: 30000, // 30 seconds socketTimeoutMS: 45000 // 45 seconds }); console.log("Server is connected to the database"); } catch (err) { console.log("Server is not connected to the database", err.message); } }; connectDb(); app.get("/", (req, res) => { res.send('Api is running on port'); }); app.use("/user", userRoutes); const PORT = process.env.PORT app.listen(PORT, console.log('Server is running on port 5050'));
userController.js
const express = require('express'); const asyncHandler = require('express-async-handler'); const UserModel = require('../Models/userModel'); const loginController = () => {}; const registerController = asyncHandler(async (req, res) => { const { name, email, password } = req.body; // Check for all fields if (!name || !email || !password) { return res.status(400).json({ message: 'All fields are required' }); } // Pre-existing user const userExist = await UserModel.findOne({ email }); if (userExist) { return res.status(400).json({ message: 'User already exists' }); } // Username already taken const userNameExist = await UserModel.findOne({ name }); if (userNameExist) { return res.status(400).json({ message: 'Username already exists' }); } // Create an entry in database for the user const user = await UserModel.create({ name, email, password }); res.status(201).json(user); }); module.exports = { loginController, registerController };
排查与解决步骤
- 验证MongoDB连接字符串正确性:检查
.env文件中的MONGO_URL是否与MongoDB Atlas控制台提供的一致,确保包含正确的用户名、密码、集群地址和数据库名称,特殊字符需做URL编码处理。 - 检查Atlas IP白名单设置:登录MongoDB Atlas控制台,确认当前服务器/本地机器的IP已添加到集群IP白名单,测试环境可临时设置为
0.0.0.0/0(生产环境需限制特定IP)。 - 确保数据库连接成功后启动服务器:修改
connectDb函数,仅在连接成功后启动服务器,避免未连接时处理请求:const connectDb = async () => { try { const connect = await mongoose.connect(process.env.MONGO_URL,{ serverSelectionTimeoutMS: 30000, socketTimeoutMS: 45000 }); console.log("Server is connected to the database"); // 连接成功后启动服务器 app.listen(PORT, () => console.log(`Server is running on port ${PORT}`)); } catch (err) { console.log("Server is not connected to the database", err.message); process.exit(1); // 连接失败退出进程 } }; connectDb(); - 禁用Mongoose查询缓冲:在连接选项中添加
bufferCommands: false,避免未连接时缓冲查询导致超时:await mongoose.connect(process.env.MONGO_URL,{ serverSelectionTimeoutMS: 30000, socketTimeoutMS: 45000, bufferCommands: false }); - 检查Mongoose版本兼容性:确保Mongoose版本与MongoDB Atlas服务器版本兼容,建议更新到最新稳定版,执行
npm update mongoose即可。 - 查看Mongoose调试日志:代码已开启
mongoose.set('debug', true),运行时查看控制台输出,获取连接失败的详细信息,定位具体问题。
内容的提问来源于stack exchange,提问作者Aman Pratap Singh
相关产品推荐
相关产品推荐

