弹性搜索:嵌套布尔过滤器中的匹配查询不起作用

3
我可以为以下 ElasticSearch 查询获取数据:

我能够获取以下 ElasticSearch 查询的数据:

{
  "query": {
    "filtered": {
      "query": [],
      "filter": {
        "bool": {
          "must": [
            {
              "bool": {
                "should": [
                  {
                    "term": {
                      "gender": "malE"
                    }
                  },
                  {
                    "term": {
                      "sentiment": "positive"
                    }
                  }
                ]
              }
            }
          ]
        }
      }
    }
  }
}

然而,如果我使用“match”进行查询,就会收到400状态响应的错误消息。
{
  "query": {
    "filtered": {
      "query": [],
      "filter": {
        "bool": {
          "must": [
            {
              "bool": {
                "should": [
                  {
                    "match": {
                      "gender": "malE"
                    }
                  },
                  {
                    "term": {
                      "sentiment": "positive"
                    }
                  }
                ]
              }
            }
          ]
        }
      }
    }
  }
}

嵌套布尔过滤器不支持匹配查询吗?

由于术语查询在字段的反向索引中查找精确术语,而我想将性别数据查询为不区分大小写的字段 - 我应该尝试哪种方法?

索引设置:

{
  "settings": {
    "index": {
      "analysis": {
        "analyzer": {
          "analyzer_keyword": {
            "tokenizer": "keyword",
            "filter": "lowercase"
          }
        }
      }
    }
  }
}

Gender字段的映射:

{"type":"string","analyzer":"analyzer_keyword"}

如果你花太多时间索引一个小写的属性,可能会更容易一些。 - john Smith
@johnSmith 我没听懂你的意思。你是说在使用term查询之前,应该将属性转换为小写吗? - Ronak Agrawal
我指的是您很可能索引对象并且在Elasticsearch中有一个映射,您可以简单地向对象类添加一个属性和一个getter函数来返回小写名称,将此字段添加到弹性映射中,这样就不会有任何问题。 - john Smith
我认为对将被索引的字段进行清理是有意义的,这样搜索引擎的整体性能才会受到最小的影响。 - john Smith
谢谢。在搜索之前,我正在对字段进行清理并将术语转换为小写(例如:{"term" : {"gender":["male"]}})。我正在寻找另一种方法。 - Ronak Agrawal
2个回答

1
您之所以会收到400错误,是因为没有match过滤器,只有match查询,尽管有term查询term过滤器。您的查询可以很简单,即不需要filtered查询,只需将termmatch查询放入bool/should中即可。
{
  "query": {
    "bool": {
      "should": [
        {
          "match": {
            "gender": "male"
          }
        },
        {
          "term": {
            "sentiment": "positive"
          }
        }
      ]
    }
  }
}

谢谢。我以为在过滤器DSL中使用match可以像对于是/否输出一样工作。除此之外,我应该使用哪种方法来进行不区分大小写的搜索 - 例如,在“情感”字段中查找“非常积极”的聚合。情感字段包含 ["积极","非常积极","消极","非常消极"]。 - Ronak Agrawal

0

这个答案适用于 ElasticSearch 7.x。从问题中我理解您想要使用 match 查询来查询 gender 字段,以及使用 term 查询来查询 sentiment 字段。每个字段的映射应该如下所示:

"sentiment": { 
       "type": "keyword" 
},
"gender": {
      "type": "text" 
}

相应的搜索 API 将会是:

"query": {
        "bool": {
            "must": [
                {
                    "terms": {
                        "sentiment": [
                            "very positive", "positive"
                        ]
                    }
                },
                {
                    "match": {
                        "gender": "malE"
                    }
                }
            ]
        }
    }

这个搜索API返回所有性别为“Male” /“MALE” /“mALe”等的文档。因此,您可能已经索引了保存“mALe”的性别字段,但是对于“gender”:“malE”的匹配查询仍然能够检索到它。在最新版本的ElasticSearch中,如果查询是match类型,则在搜索开始之前,值(即“gender”:“malE”)将在内部自动转换为小写。但是,API的客户端应该很容易在一开始就将小写传递给匹配查询。至于sentiment字段,由于它是一个keyword字段,因此您可以搜索包含空格的值,例如very positive


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接