成功案例
1.按照官网的使用方法进行抽离封装(这里是一个insert方法)
2.config.js
把导入的变量封装成一个config.js文件
3.db.js
创建Db类的模块db.js
这里把MongoClient实例放在了Db类实例的clint属性上
连接数据库的方法,用Promise获取db实例
插入方法:用了 async 和 await 来获取 this.count() 执行完毕后 返回的Promise实例中的db
结果:成功插入数据库
开始遇坑
思考:insert方法上用了async和await ,不如把connect方法也改成用async和await,这样可以简洁很多
改好了!
运行!
直接报错!
这说的什么呢?
TypeError: Cannot read property 'collection' of undefined
async function without a catch block
这里有2个主要问题 (1.db实例里的 collection 没有定义)
打印db实例 => 结果是undiluted => 进而推导是因为 return db时有错误抛出又没人接收
导致报 (2.async function without a catch block 错误)
下面进行错误接收:
运行还是报错,原因依旧是没有接收错误的catch。难道 try catch要用来裹 this.clint.connect => 直接否定 => this.clint.connect 是个异步操作,try catch 只能检测同步代码
eq:原因如下
如果包裹了this.clint.connect 鬼知道你什么时候 throw err ,catch自然捕获不到数据
既然try catch没有写错,那为什么还是报错呢?
问题重点出在 db 为 undiluted 的句子上
不卖关子,直接说原因吧。
这里是重点:await 只能接收 Promise 实例!!!
1.上面 return db 的 db 如果(不是 Promise 实例 || 是Promise 实例,但没有给resolve传值) => await 默认会 new Promise()而且resolve(undfined) 。看到undefined没?这就是来源。
2.然后 return db 的 db 为什么不是Promise实例 ,因为this.clint.connect根本不是以Promise为原型来封装的,讲到这里欲哭无泪啊。在this.clint.connect的回调函数中返回的不是个Promise啊
误解来源:为什么自己会不由的以为mongo模块是可以返回Promise的,因为axios模块就是用Promise原型封装的模块 (- 。-)
结论:慎重使用async和await,在并发的异步函数中进行汇总处理也不要用await,而是用Promise.all