mongoose连接本地MongoDB调用findOne报TypeError如何修复
问题场景
需要通过服务端连接本地部署的外部MongoDB数据库,读取本地库(而非服务端自带数据库)中存储的Price模型数据,初始实现代码如下:
const mongooseLocal = require('mongoose'); const connectionOptions = { useCreateIndex: true, useNewUrlParser: true, useUnifiedTopology: true, useFindAndModify: false }; const conn = mongooseLocal.createConnection(config.MONGODB_URI_LOCAL, connectionOptions); conn.on("error", console.error.bind(console, "connection error: ")); conn.once("open", async () => { console.log("Connected successfully"); const priceModel = await conn.Price.findOne({}); // Price 是本地库中存在的模型,服务端侧未定义 console.log('init', priceModel); });
运行时可以正常打印Connected successfully连接成功日志,但无法读取目标数据,抛出如下错误:
TypeError: Cannot read property 'findOne' of undefined
错误原因
使用mongoose.createConnection()创建的数据库连接实例,不会自动加载对应库中已存在的模型,直接访问conn.Price时该属性不存在,因此拿到undefined,调用findOne方法就会触发类型错误。
Mongoose操作MongoDB集合的前提是,需要在当前连接实例上注册对应集合的Schema与模型,才能获得可操作的模型实例。
修复步骤
- 定义Price集合对应的Schema,字段和本地库中Price集合的实际结构匹配即可,不需要全量覆盖所有字段,只需要声明查询要用到的字段
- 在创建的连接实例
conn上,通过conn.model()方法注册Price模型,如果本地集合名不是Mongoose默认生成的小驼峰转小写复数格式(即模型名Price默认对应prices集合),需要手动传入第三个参数指定真实集合名 - 使用注册完成的模型实例执行查询操作
修复后的完整代码:
const mongooseLocal = require('mongoose'); const connectionOptions = { useCreateIndex: true, useNewUrlParser: true, useUnifiedTopology: true, useFindAndModify: false }; const conn = mongooseLocal.createConnection(config.MONGODB_URI_LOCAL, connectionOptions); // 定义Price集合对应的Schema,按实际字段补充 const priceSchema = new mongooseLocal.Schema({ // 示例字段,替换为你本地Price集合的真实字段 goodsName: String, price: Number, updateTime: Date }, { versionKey: false }); // 在连接实例上注册模型,第三个参数替换为你本地Price存储的真实集合名 const PriceModel = conn.model('Price', priceSchema, 'prices'); conn.on("error", console.error.bind(console, "connection error: ")); conn.once("open", async () => { console.log("Connected successfully"); const priceModel = await PriceModel.findOne({}); console.log('init', priceModel); });
注意:如果注册模型时未指定正确的集合名,Mongoose会按照默认规则生成集合名,会出现查询不到数据的问题,需要和本地库的实际集合名保持一致。
内容的提问来源于stack exchange,提问作者Sara Ree
相关产品推荐
相关产品推荐

