如何在Mongo/Mongoose的$or查询中条件性增减查询条件?
问题
需要编写一个接收search和category两个参数的Mongo/Mongoose查询,返回满足以下任一条件的记录:
productModel.name包含searchproductModel.description包含searchproductModel.category包含category
原写法在search或category参数缺失时会失效:
return this.productModel.find({ $or: [ { name: { $regex: search, $options: 'i' } }, { description: { $regex: search, $options: 'i' } }, { category: { $regex: category, $options: 'i' } }, ], });
目前通过三个条件分支处理,但希望用更优雅的单查询实现:
if (!category) { return this.productModel.find({ $or: [ { name: { $regex: search, $options: 'i' } }, { description: { $regex: search, $options: 'i' } }, ], }); } if (!search) { return this.productModel.find({ category: { $regex: category, $options: 'i' }, }); } return this.productModel.find({ $or: [ { name: { $regex: search, $options: 'i' } }, { description: { $regex: search, $options: 'i' } }, { category: { $regex: category, $options: 'i' } }, ], });
询问是否存在优雅的单查询方式处理参数的条件性存在。
优雅的单查询实现方式
可以通过动态构建查询条件数组的方式实现单查询,只在参数存在时添加对应的查询条件,最后根据条件数组的长度决定是否使用$or:
const conditions = []; // 当search参数存在时,添加name和description的模糊匹配条件 if (search) { conditions.push( { name: { $regex: search, $options: 'i' } }, { description: { $regex: search, $options: 'i' } } ); } // 当category参数存在时,添加category的模糊匹配条件 if (category) { conditions.push({ category: { $regex: category, $options: 'i' } }); } // 根据条件数组长度构建查询 const query = conditions.length > 1 ? { $or: conditions } : conditions[0] || {}; return this.productModel.find(query);
逻辑说明
- 先初始化一个空的条件数组
conditions - 分别判断
search和category参数是否存在,存在则将对应的查询规则推入数组 - 最后根据数组长度处理:
- 如果数组长度大于1,用
$or包裹所有条件 - 如果数组长度为1,直接使用该条件(无需
$or) - 如果两个参数都缺失,返回空查询(即所有记录,可根据业务需求调整为返回空数组或其他逻辑)
- 如果数组长度大于1,用
这种方式既避免了多分支判断,又能灵活处理参数的存在性,代码更简洁易维护。
内容的提问来源于stack exchange,提问作者DukeSmellington
相关产品推荐
相关产品推荐

