我无法将结果集限制为同时匹配下面两个kol_tags.scored.name
选项的kol_tags.scored.score
和or
范围的文档。
我想匹配kol_tags.scored.name
为“Core Grower”和kol_tags.scored.score
在1到100之间的文档,除非它们也具有kol_tags.scored.name
为而不是在35到65之间的“Connectivity”的kol_tags.scored.score
。
给定以下映射(为简洁起见,省略了非嵌套字段):
GET /production_users/user/_mapping
{
"user": {
"_all": {
"enabled": false
},
"properties": {
"kol_tags": {
"type": "nested",
"properties": {
"scored": {
"type": "nested",
"properties": {
"name": {
"type": "string",
"index": "not_analyzed",
"omit_norms": true,
"index_options": "docs"
},
"score": {
"type": "integer"
}
}
}
}
}
}
}
}
我正在执行以下查询:
{
"filter": {
"nested": {
"path": "kol_tags.scored",
"filter": {
"or": [
{
"and": [
{
"terms": {
"kol_tags.scored.name": [
"Core Grower"
]
}
},
{
"range": {
"kol_tags.scored.score": {
"gte": 1,
"lte": 100
}
}
}
]
},
{
"and": [
{
"terms": {
"kol_tags.scored.name": [
"Connectivity"
]
}
},
{
"range": {
"kol_tags.scored.score": {
"gte": 35,
"lte": 65
}
}
}
]
}
]
}
}
}
}
通过上面的查询,我得到的文档匹配“Core Grower”的
kol_tags.scored.name
和介于1到100之间的kol_tags.scored.score
和 ALSO ,它们的kol_tags.scored.name
为“Connectivity”和kol_tags.scored.score
在任何范围内。我需要的是符合条件的文件:
“Core Grower”的
kol_tags.scored.name
和1至100之间的kol_tags.scored.score
kol_tags.scored.name
和35到65之间的kol_tags.scored.score
kol_tags.scored.name
为“连通性”且kol_tags.scored.score
小于34且大于66的所有文档 最佳答案
您的描述中有一些歧义,但我尝试制作一个可运行的示例,该示例在这里应适用:https://www.found.no/play/gist/8940202(也嵌入在下面)
这是我做的几件事:
filtered
-query中。仅当您要过滤匹配时,而不是构面时,才应使用顶级filter
(在Elasticsearch 1.0中重命名为post_filter
)。 bool
而不是and
和or
,因为过滤器是可缓存的。此处更多信息:http://www.elasticsearch.org/blog/all-about-elasticsearch-filter-bitsets/ nested
放在bool
内,这样逻辑就可以正确地实现了。嵌套文档与父文档应该匹配什么。 must_not
以说明您的最后一点。不知道您是否可以拥有两个名为"Connectivity"
的子文档,但是如果可以的话,应该可以解决这个问题。如果您只有一个,则可以删除must_not
。 您没有提供任何示例文档,所以我提出了一些我认为适合您的描述的文档。我认为您不需要两个级别的嵌套。
#!/bin/bash
export ELASTICSEARCH_ENDPOINT="http://localhost:9200"
# Create indexes
curl -XPUT "$ELASTICSEARCH_ENDPOINT/play" -d '{
"mappings": {
"type": {
"properties": {
"kol_tags": {
"properties": {
"scored": {
"type": "nested",
"properties": {
"name": {
"type": "string",
"index": "not_analyzed"
}
}
}
}
}
}
}
}
}'
# Index documents
curl -XPOST "$ELASTICSEARCH_ENDPOINT/_bulk?refresh=true" -d '
{"index":{"_index":"play","_type":"type"}}
{"kol_tags":{"scored":[{"name":"Core Grower","score":36},{"name":"Connectivity","score":42}]}}
{"index":{"_index":"play","_type":"type"}}
{"kol_tags":{"scored":[{"name":"Connectivity","score":34},{"name":"Connectivity","score":42}]}}
{"index":{"_index":"play","_type":"type"}}
{"kol_tags":{"scored":[{"name":"Core Grower","score":36}]}}
{"index":{"_index":"play","_type":"type"}}
{"kol_tags":{"scored":[{"name":"Connectivity","score":36}]}}
'
# Do searches
curl -XPOST "$ELASTICSEARCH_ENDPOINT/_search?pretty" -d '
{
"query": {
"filtered": {
"filter": {
"bool": {
"should": [
{
"nested": {
"path": "kol_tags.scored",
"filter": {
"bool": {
"must": [
{
"term": {
"name": "Core Grower"
}
},
{
"range": {
"score": {
"gte": 1,
"lte": 100
}
}
}
]
}
}
}
},
{
"nested": {
"path": "kol_tags.scored",
"filter": {
"bool": {
"must": [
{
"term": {
"name": "Connectivity"
}
},
{
"range": {
"score": {
"gte": 35,
"lte": 65
}
}
}
]
}
}
}
}
],
"must_not": [
{
"nested": {
"path": "kol_tags.scored",
"filter": {
"bool": {
"must": [
{
"term": {
"name": "Connectivity"
}
},
{
"not": {
"range": {
"score": {
"gte": 35,
"lte": 65
}
}
}
}
]
}
}
}
}
]
}
}
}
}
}
'
curl -XPOST "$ELASTICSEARCH_ENDPOINT/_search?pretty" -d '
{
"filter": {
"nested": {
"path": "kol_tags.scored",
"filter": {
"or": [
{
"and": [
{
"terms": {
"kol_tags.scored.name": [
"Core Grower"
]
}
},
{
"range": {
"kol_tags.scored.score": {
"gte": 1,
"lte": 100
}
}
}
]
},
{
"and": [
{
"terms": {
"kol_tags.scored.name": [
"Connectivity"
]
}
},
{
"range": {
"kol_tags.scored.score": {
"gte": 35,
"lte": 65
}
}
}
]
}
]
}
}
}
}
'
关于search - 具有排除OR的嵌套过滤器查询,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/21691882/