如何根据用户输入在mongoDB中聚合数据?

时间:2019-05-28 10:35:13

标签: node.js mongodb express aggregate

我想在mongoDB中使用聚合框架根据用户输入来查询数据库。我创建了一个应用程序,在该应用程序中,在键入每个字母后,提取会检索所有匹配的数据。输入的字母越多,输出范围越窄。

示例

用户输入字母 G ,输出为10条JSON记录。 用户输入商誉,输出为1(只有一条记录与单词“商誉”匹配)

问题

我必须在我的所有JSON键值对中搜索每个键入的字母数字。如果用户键入任何内容,我必须搜索标题 headerNum 内容 contentNum 详细信息

当前,我已经解决了这个问题,但这是一种解决方法。我在mongoDB find()方法中使用了 RegExp 来满足预期条件。然后,我使用 map()过滤所有与用户搜索匹配的结果。

JSON

        "header": "Intangible assets",
        "headerNum": "10",
        "meta": [
            {
                "meta_id": "1",
                "header": "Intangible assets",
                "headerNum": "10",
                "content": "Random content and goodwill",
                "contentNum": "1080",
                "details": "Some random text with the word goodwill",
                "tags": ["goodwill"]
            }
        ]
    }

条件

const search = req.query.term.toLowerCase();
const regExp = new RegExp(".*" + search + ".*", "gi");

    let conditions = [{
            "meta.header": regExp
        },
        {
            "meta.tags": regExp
        },
        {
            "meta.content": regExp
        },
        {
            "meta.details": regExp
        }
    ];

    if (typeof parseInt(search) === 'number') {
        conditions.push({"meta.headerNum": regExp}, {"meta.contentNum": regExp});
    }

使用查找和地图创建查询

db.getDB()
        .collection(collection)
        .find({
            $or: conditions
        })
        .map(function(record) {
            if (record.header.includes(search) || record.headerNum.includes(search)) {
                return record;
            }

            record.meta = record.meta.filter(function(meta) {
                return meta.tags.find(function(tag) {
                    return tag.toLowerCase().includes(search)
                }) || meta.content.toLowerCase().includes(search) ||
                meta.details.toLowerCase().includes(search) || meta.contentNum.toLowerCase().includes(search)
            });
            return record;
        })
        .sort({headerNum: 1})
        .toArray((err, docs) => {
            if (err) {
                console.log(err);
            } else {
                res.json(docs.filter(function(record) { 
                    return record.meta.length;
                }));
            };
        });

我想用聚合替换查找和映射。我正尝试通过放卷来做到这一点,但没有令人满意的结果。预先感谢!

0 个答案:

没有答案