node.js - 如何构建动态 MongoDB 查询
问题描述
我有 2 个集合 MongoDB。关键字和个人信息。我从客户端收到一个数组,如下所示:
[
{fieldName : 'Keyword',operator: '===',value: 'soccer'},
{fieldName : 'Keyword',operator: 'endsWith',value: 'cer'},
{fieldName : 'Name',operator: 'startsWith',value: 'mik'}
]
我正在使用需要动态构建 MongoDB 查询的 NodeJs。我试过这样。
let q = {};
q["$and"] = [];
let data = req.body;
for (let i = 0; i < data.length; i++) {
// I tried without consideration of "operator" first but couldn't succeed.
let val = new RegExp(data[i].value);
if (data[i].fieldName === "Keyword") {
q["$and"].push({ Keyword: { $regex: val, $options: "-i" } });
} else if (data[i].fieldName === "Name") {
q["$and"].push({ Name: { $regex: val, $options: "-i" } }); //Since this field is from another collection, so instead of Name i want to push it as "$$name" so i could be able to use it in aggregates.
}
}
我期待看到这样的输出。
{$and:
[
{Keyword: {$regex: 'search val', $options: "-i"}},
{Name: {$regex: 'search val', $options: "-i"}},
]
}
但我得到的是:
{$and:
[
{Keyword: [Object]},
{Name: [Object]},
]
}
我如何构建上述查询并在聚合中实现它;
await Keyword.aggregate([
{
$lookup: {
from: "PersonalInfo",
let: { name: "$Name" },
pipeline: [{ $match: { $expr: q } }],
as: "searchRecords"
}
}
])
这是我的完整代码。
let q = {};
let results;
let data = req.body;
let and_conds = [];
for (let i = 0; i < data.length; i++) {
let val = new RegExp(data[i].value);
let field_name = data[i].fieldName;
and_conds.push({ [field_name]: { $regex: val, $options: "-i" } });
}
q["$and"] = and_conds;
let records = await KeyInfo.aggregate([
{
$lookup: {
from: "PersonalInfo",
let: { name: "$name" },
pipeline: [{ $match: { $expr: q } }],
as: "searchRecords"
}
}
]);
感谢您的宝贵时间并感谢您的帮助。
解决方案
你做得对,我不确定你是如何得到你的“输出”(假设你打印了它),但它只是向你展示了你的对象内部的内容,这是预期的另一个对象。
完整的代码如下所示:(为了便于阅读,稍微清除了一点)
let q = {};
let data = req.body;
let and_conds = [];
for (let i = 0; i < data.length; i++) {
let val = new RegExp(data[i].value);
let field_name = data[i].fieldName;
and_conds.push({[field_name]: { $regex: val, $options: "-i" }})
}
q["$and"] = and_conds;
- 我不确定您的
$$name
评论是什么意思,因为您在匹配阶段查找后仅使用这些条件,但如果您所要做的就是将field_name
值从更改"Name"
为"$$name"
。
编辑:
使用它而不是上面的语法:
let val = new RegExp(data[i].value, "i");
and_conds.push({[field_name]: val)`
你也没有改变你fieldName
,"$$name"
你也应该这样做。
推荐阅读
- testng - KotlinTest 是否也支持 TestNG?
- sequence - odoo 10 中的测序
- angular - 如何删除下划线并在有角材料组件周围提供一个框?
- openxlsx - 防止 writeDataTable (openxlsx) 写入任何列名
- angularjs - AngularJS 使用默认参数删除哈希 (#)
- c# - 将大型 3rd 方 dll 拆分为较小的部分
- amazon-web-services - AWS Glue + Athena/Hive 是替代复杂 SQL 查询的正确选择吗?
- javascript - Javascript 日期 setMonth 未正确设置月份
- prestashop-1.7 - Prestashop 1.7 总计计算不正确
- android - KeyNotFoundException:找不到 WCFManager.ViewModels.SettingsViewModel 的视图