[ElasticSearch]ES操作之嵌套查询(nested)与退出嵌套(reverse_nested)操作

Posted nysd

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[ElasticSearch]ES操作之嵌套查询(nested)与退出嵌套(reverse_nested)操作相关的知识,希望对你有一定的参考价值。

嵌套类型的基本概念就不讲了,需要了解概念的,传送门:https://www.cnblogs.com/just84/p/10936034.html

 

对于嵌套类型的字段,要使用ES专用的嵌套查询

 

嵌套字段举例:

      brandInfo:[
?            {
?              "group": "xx",
?              "category": "xx",
?              "subCategory": "xx",
?              "brand": "xx",
?              "subBrand": "xx",
?              "propertyWord": [
?                "xx",
?                "xx",
?                "xx"
?              ]
?            }
      ]

 

如果要获取subBrand的分组  就需要这样实现:

    "aggs": {
        "brandInfo": {
          "nested": {
            "path": "brandInfo"
          },
          "aggs": {
            "brands": {
              "terms": {
                "field": "brandInfo.subBrand",
                "size": xx
              }
            }
          }
        }
      }

 

如果要在subBrand分组的条件上,进行propertyWord的分组,也很简单:

    "aggs": {
        "brandInfo": {
          "nested": {
            "path": "brandInfo"
          },
          "aggs": {
            "brands": {
              "terms": {
                "field": "brandInfo.subBrand",
                "size": 10
              },
              "aggs": {
                "property": {
                  "terms": {
                    "field": "brandInfo.propertyWord",
                    "size": 100
                  }
                }
              }
            }
          }
        }
      }

 

需求往往是多变的

如果突然在subBrand的分组下,还要进行 非嵌套字段 的分组,比如名称,性别,年龄等,如何实现呢?

这个时候一般都会想,和上边一样呗,如下:

    "aggs": {
        "brandInfo": {
          "nested": {
            "path": "brandInfo"
          },
          "aggs": {
            "brands": {
              "terms": {
                "field": "brandInfo.subBrand",
                "size": 3
              },
         "aggs": {
                 "gender": {
                   "terms": {
                     "field": "gender",
                     "size": 3
                   }
                 }
               }
            }
            }
          }
        }

但这样是查不到性别分组数据的

原因是:  进入了嵌套桶中,只能操作嵌套字段.

 

后来了解到,可以通过 reverse_nested  跳出当前嵌套,并且  依然携带之前的分组条件   

    "aggs": {
        "brandInfo": {
          "nested": {
            "path": "brandInfo"
          },
          "aggs": {
            "brands": {
              "terms": {
                "field": "brandInfo.subBrand",
                "size": 3
              },
              "aggs": {
                "rev": {
                  "reverse_nested": {},  //跳出嵌套桶
                  "aggs": {
                    "age": {
                      "terms": {
                        "field": "gender",
                        "size": 3
                      }
                    }
                  }
                }
              }
            }
          }
        }
      }

问题解决.

 

用java实现也很简单,相关的嵌套和跳出嵌套代码片段:

//解析嵌套字段
Map<String, Aggregation> brandInfo =((Nested) result.get("brandInfo")).getAggregations().getAsMap();
//品牌
List<Terms.Bucket> bucketList = ((Terms) brandInfo.get("brands")).getBuckets();
for (Terms.Bucket bucket : bucketList) {
  //跳出嵌套
  Map<String, Aggregation> revInfo =((ReverseNested) bucket.getAggregations().get("rev")).getAggregations().getAsMap();
  //一级维度
  List<Terms.Bucket> genders = ((Terms) revInfo.get("gender")).getBuckets();
  //封装数据
  for (Terms.Bucket gender : genders) {
    //TODO
  }
}

 

以上是关于[ElasticSearch]ES操作之嵌套查询(nested)与退出嵌套(reverse_nested)操作的主要内容,如果未能解决你的问题,请参考以下文章

Elasticsearch 7.x Nested 嵌套类型查询 ES 干货

Elasticsearch之JavaAPI操作ES

跟我学Elasticsearch(7) es的嵌套聚合,下钻分析,聚合分析

Elasticsearch es nested 嵌套类型 详解

Elasticsearch连续剧之实战篇Java操作es

elasticsearch的嵌套查询nested