尝试过滤一些字段可能不存在的 Elasticsearch 结果

Trying to filter some Elasticsearch results where the field might not exist

我有一些数据,我正在尝试添加一个额外的过滤器,该过滤器将 exclude/filter-out key/value 为 foo.IsMarried == true 的任何结果。

现在,有大量文档没有此字段。如果该字段不存在,那么我假设该值为 foo.IsMarried = false .. 因此这些文档将包含在结果集中。

谁能提供线索,好吗?

我也在使用 .NET 'NEST' nuget 客户端库 - 所以如果答案可以针对那个,我将非常感激,但对任何答案都很满意,真的。

您可以在以下条件下使用 should 查询。

  1. IsMarried = false
  2. 不得存在 IsMarried
POST test/person/
{"name": "p1", "IsMarried": false}

POST test/person/
{"name": "p2", "IsMarried": true}

POST test/person/
{"name": "p3"}

Raw DSL query

POST test/person/_search
{
  "query": {
    "bool": {
      "should": [
        {
          "match": {
            "IsMarried": false
          }
        },
        {
          "bool": {
            "must_not": {
              "exists": {
                "field": "IsMarried"
              }
            }
          }
        }
      ]
    }
  }
}

我希望你能将这个原始 DSL 查询转换为 NEST!

一般来说,在elasticsearch中,对于一个boolean字段,如果该字段不存在,并不代表它的值为false。可能是没有反对的价值。

但是,根据您在这种情况下所做的假设 - 我们可以检查字段 foo.isMarried 是否明确为假 OR 它在文档本身中不存在。 Rahul 在另一个答案中提出的查询可以完成这项工作。但是,由于您想要相同的 NEST 版本,因此可以使用以下代码片段构建查询。

// Notice the use of not exists here. If you do not want to check for the 'false' value,
// you can omit the first term filter here. 'T' is the type to which you are mapping your index.
// You should pass the field based on the structure of 'T'.
private static QueryContainer BuildNotExistsQuery()
{
    var boolQuery = new QueryContainerDescriptor<T>().Bool(
        b => b.Should(
            s => s.Term(t => t.Field(f => f.foo.IsMarried).Value(false)),
            s => !s.Exists(ne => ne.Field(f => f.foo.IsMarried))
        )
    );
}

您可以通过项目中的 NEST 客户端触发搜索,如下所示。

var result = client.Search<T>(    
    .From(0)
    .Size(20)
    .Query(q => BuildNotExistsQuery())
    // other methods that you want to chain go here
)