我有一个弹性搜索索引,其中包含以下映射:
{
"index_one": {
"mappings": {
"uidMapping": {
"_all": {
"enabled": false
},
"_source": {
"enabled": false
},
"properties": {
"age": {
"type": "keyword"
},
"clean_url": {
"type": "keyword",
"index": false,
"fields": {
"hash": {
"type": "murmur3"
}
}
},
"gender": {
"type": "keyword"
},
"segment_aggregate": {
"properties": {
"segment_name": {
"type": "keyword"
},
"segment_value": {
"type": "keyword"
}
}
},
"url_md5": {
"type": "keyword",
"index": false
},
"url_page_views": {
"type": "integer",
"index": false
}
}
}
}
}
}
我正在尝试在segment_aggregate字段上运行带有AND操作的查询,即只有在满足两个条件时才会返回查询结果。到目前为止,使用BoolQueryBuilders,我在Must子句中尝试了匹配查询和术语查询,但似乎总是在segment_name和segment_value之间获得结果或操作。
BoolQueryBuilder queryTest = new BoolQueryBuilder();
queryTest.must(QueryBuilders.matchQuery("segment_aggregate.segment_name",
"AnyValue").operator(Operator.AND));
queryTest.must(QueryBuilders.matchQuery("segment_aggregate.segment_value",
"A").operator(Operator.AND));
parentQuery.must(queryTest);
这将返回两个字段的OR结果,基本上是较大的子集。 还试过:
mustQuery.must(QueryBuilders.termsQuery("segment_aggregate.segment_name", "SegmentName"));
mustQuery.must(QueryBuilders.termsQuery("segment_aggregate.segment_value", "SegmentValue"));
这也不会产生欲望的结果。 即使我尝试在另一个查询中使用must子句包装子查询,并添加到父查询,这种方法也不起作用。
关于我哪里出错的任何想法?
答案 0 :(得分:1)
您看到的问题可能是因为您没有将segment_aggregate类型标记为嵌套。
默认情况下,所有字段都是独立索引的。即使JSON结构看起来像是将segment_aggregate中的内部对象内的特定值关联在一起,但实际上ES正在为 segment_aggregate.segment_name 创建值的索引,并为 segment_aggregate.segment_value创建单独的索引。 即可。
这意味着当你进行这样的搜索时(假设查询字符串):
segment_aggregate.segment_name:color AND segment_aggregate.segment_value:green
Elasticsearch真正在做的是搜索文档,其中 segment_aggregate.segment_name 中的任何值都设置为" color" segment_aggregate.segment_value 中的任何值都设置为"绿色"。要告诉Elasticsearch您想要使用内部对象中的字段之间的关联,您需要将 segment_aggregate' s 类型标记为"嵌套"而不是"对象"的默认值。此外,您还需要使用查询DSL的特殊嵌套查询和嵌套聚合部分。
更多细节可以在这里找到: https://www.elastic.co/guide/en/elasticsearch/reference/current/nested.html