在反向嵌套字段上对多个值进行计数聚合

时间:2019-09-13 13:15:01

标签: elasticsearch

我们的弹性映射

 {"mappings": {
         "products" : {
          "properties":{
             "name " : {
               "type" : "keyword"
             },
             "resellers" : { 
                 "type" : "nested",
                 "properties" : {
                     "name" : { "type" : "text" },
                     "price" : { "type" : "double" }
                 }
             }
           }
         }
     }}

在此映射中,每个产品都存储以特定价格出售产品的经销商列表。

我们有要求,我们希望获得特定经销商以特定价格出售的产品数量,我可以通过以下查询DSL使用反向嵌套agg和基数agg来获得单个经销商的数量 。例如:-取得Amazon出售产品的总价为2。

 {
      "query": {
        "bool": {
          "must": [
            {
              "match_all": {
                "boost": 1.0
              }
            }
          ]
        }
      },
      "aggs": {
        "patchFilter": {
          "nested": {
            "path": "resellers"
          },
          "aggs": {
            "nestedfilter": {
              "filter": {
               "bool": {
                 "must":[
                   {
                     "term" :{
                       "resellers.name.keyword": {
                      "value": "Amazon"
                    }
                     }
                   },{
                     "terms" :{
                       "resellers.price":[2]
                     }
                   }
                   ]
               }
              },
              "aggs": {
               "resellerprice": {
                        "reverse_nested" :{},
                     "aggs": {
                       "resellers_price":{
                               "cardinality" : {
                                    "field" : "name.keyword"
                                 }
                             }
                }
              }
            }
          }
        }
      }
    }
    }

我想为多个经销商(亚马逊,Flipkart,沃尔玛)在单个查询中以2个价格出售它。有人可以帮我吗?

1 个答案:

答案 0 :(得分:1)

映射:

PUT productreseller
{
  "mappings": {
      "properties": {
        "name": {
          "type": "keyword"
        },
        "resellers": {
          "type": "nested",
          "properties": {
            "name": {
              "type": "text",
               "fields":{
                 "keyword":{
                   "type": "keyword"
                 }
               }
            },
            "price": {
              "type": "double"
            }
          }
        }
      }
    }
  }

数据:

 [
      {
        "_index" : "productreseller",
        "_type" : "_doc",
        "_id" : "JNbCLm0B00idyGV0Pn1Z",
        "_score" : 1.0,
        "_source" : {
          "name" : "P2",
          "resellers" : [
            {
              "name" : "amazon",
              "price" : 3
            },
            {
              "name" : "abc",
              "price" : 2
            }
          ]
        }
      },
      {
        "_index" : "productreseller",
        "_type" : "_doc",
        "_id" : "JdbCLm0B00idyGV0Wn0y",
        "_score" : 1.0,
        "_source" : {
          "name" : "P1",
          "resellers" : [
            {
              "name" : "amazon",
              "price" : 2
            },
            {
              "name" : "abc",
              "price" : 3
            }
          ]
        }
      },
      {
        "_index" : "productreseller",
        "_type" : "_doc",
        "_id" : "JtbPLm0B00idyGV0D32Y",
        "_score" : 1.0,
        "_source" : {
          "name" : "P4",
          "resellers" : [
            {
              "name" : "xyz",
              "price" : 2
            },
            {
              "name" : "abc",
              "price" : 3
            }
          ]
        }
      }
]

查询:

GET productreseller/_search
{
  "query": {
    "bool": {
      "must": [
        {
          "match_all": {
            "boost": 1
          }
        }
      ]
    }
  },
  "aggs": {
    "patchFilter": {
      "nested": {
        "path": "resellers"
      },
      "aggs": {
        "nestedfilter": {
          "filter": {
            "bool": {
              "must": [
                {
                  "terms": {
                    "resellers.price": [
                      2
                    ]
                  }
                }
              ]
            }
          },
          "aggs": {
            "NAME": {
              "terms": {
 --->terms aggregation to list resellers and reverse_nested as subaggregation
                "field": "resellers.name.keyword",
                "size": 10
              },
              "aggs": {
                "resellerprice": {
                  "reverse_nested": {},
                  "aggs": {
                    "resellers_price": {
                      "cardinality": {
                        "field": "name"
                      }
                    }
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}

结果:

"aggregations" : {
    "patchFilter" : {
      "doc_count" : 8,
      "nestedfilter" : {
        "doc_count" : 3,
        "NAME" : {
          "doc_count_error_upper_bound" : 0,
          "sum_other_doc_count" : 0,
          "buckets" : [
            {
              "key" : "abc",
              "doc_count" : 1,
              "resellerprice" : {
                "doc_count" : 1,
                "resellers_price" : {
                  "value" : 1
                }
              }
            },
            {
              "key" : "amazon",
              "doc_count" : 1,
              "resellerprice" : {
                "doc_count" : 1,
                "resellers_price" : {
                  "value" : 1
                }
              }
            },
            {
              "key" : "xyz",
              "doc_count" : 1,
              "resellerprice" : {
                "doc_count" : 1,
                "resellers_price" : {
                  "value" : 1
                }
              }
            }
          ]
        }
      }
    }
  }

如果您只想显示某些代理商,则可以在嵌套过滤器中添加字词查询