如何在MongoDB非索引字段上有效地执行复杂查询?

时间:2018-04-02 16:14:40

标签: mongodb elasticsearch

我正在为Web应用程序构建过滤功能,它应该看起来像TFS过滤查询的JIRA。因此,用户应该能够过滤字段内容并在过滤查询中使用逻辑运算符。

数据存在于MongoDB中,主要的挑战是我们将过滤的字段不仅应该支持严格的相等而且还要支持全文搜索,因为它们可能因每个用户而异。

简而言之,有一个嵌套对象,它有三个其他嵌套对象,根据用户可以有不同数量的字段,字段名也是由用户设置的,所以我们不了解它们。

例如,集合中的文档结构可以是:

{
_id: ObjectId()
storage: {
obj_1:{}
obj_2:{}
         }
},
{
_id: ObjectId()
storage: {
obj_1:{
field_1 : val,
field_2 : val
}
obj_2:{}
         }
}

我想象查询会是这样的:

find({$and:[{"storage.obj_1.field_1":{$regex: "va"}},{"storage.obj_1.var_2":"val"}]})

不幸的是,我不是数据库专家,所以我现在看到的解决方案是:

1)使用Elasticsearch作为搜索引擎。 但问题是:如果我不了解我的文档结构,如何设置弹性索引?

2)在Mongo中使用稀疏索引。但我需要使用正则表达式进行匹配,该解决方案是否优于Elastic?

所以问题是:在这种数据库结构中进行过滤的最佳方法是什么?

P.S。 我已经把这个问题放在SO而不是软件工程中,因为SO有更多的活跃成员,请保留你的downvotes以供日后使用

1 个答案:

答案 0 :(得分:1)

  1. Elasticsearch和MongoDB(很像关系数据库)对索引的行为有所不同:在MongoDB中,您需要显式索引每个字段(对于非$text索引)。在Elasticsearch中,每个字段都会自动编入索引。不要对Elasticsearch中的字段数量过于疯狂,因为每个字段都有一点开销(就磁盘空间而言,虽然在版本6中有所改进)。
  2. 只要您拥有多个测试数据集,正则表达式通常很慢,因为它们只能使用specific cases中的索引,您需要明确定义这些索引。也许$text索引和搜索运算符更符合您的需求。那个也可以在集合中索引every field。如果您需要更多功能和完全构建用于搜索的系统,那么Elasticsearch将是更好的选择。