作者:中农数智信息科技有限公司-工程师-DaZuiYu-CD
校和:中农数智信息科技有限公司-产品研发经理-MrCare
本文正在参加「技术专题19期 漫谈数据库技术」活动
技术点产生的背景
在土壤质量评价工具的开发过程中,采用了层次分析法来评价土壤质量等级,层次分析法的核心概念是指标和准则,从准则的维度将指标进行分组,然后进行打分评价,其中准则和指标数据的形式是一条条的记录,并且指标和准则间存在多对一的关系,在本项目的开发过程中,应用了MongoDB与ts-node作为主要数据库和开发语言,应用了mongoose作为ORM工具,在开发过程中,利用了mongoose 虚拟字段和聚合查询的高级特性,实现了快速的“联表查询”业务层开发,并将开发过程中的细节记录于此,作为一点一滴的技术总结。
联表查询的两种方法
虚拟字段
创建指标表,其中standard字段指向准则表
创建准则表,并添加虚拟字段
使用:
await standardModel.find().populate('standardList')
数据:
- 准则表
- 指标表
结果:
聚合查询
使用mongoose的aggregate API:
mongoosejs.com/docs/api/mo…
mongoosejs.com/docs/api/ag…
www.mongodb.com/docs/manual…
使用方法与虚拟字段类似,也可以使用链式调用方式
返回对象修改字段与解构赋值失败问题
Mongoose查询返回的对象是不能直接修改的 原因: 查询返回的对象类型为mongoose.document mongoosejs.com/docs/api/do… 在输出或返回时,会自动调用toObject/toJSON方法,所以显示和接口返回时正常的。不能直接对其进行修改或添加字段。解构赋值也会出现解构后的字段与预期不符的问题。 解决方法:
- 在查询后调用.lean()方法
- 在查询结果document上调用toObject或者toJSON
toObject与toJSON的区别:
- 两者本质上是一样的,是同一种方法使用两种不同的模式进行调用。如果有在schema中对其进行配置(如transform等),则会产生区别。
- mongoose只有在返回http 的response 的时候,才会调用toJSON 函数。doc 在其他场景下,包括在内存中的读写等,调用的都是toObject()函数。