在瞭解本文內容前,必須先了解ES DSL查詢和ES 聚合查詢,ES基於查詢結果的聚合分爲兩種,第一種類似與關係型數據庫中的Having語法,第二種類似於關係型數據庫中先where在group by的語法,本文主要分析先查詢後聚合場景
演示數據從ES 聚合查詢獲取
1、先查詢後聚合
現在需要統計價格在50到500價格範圍區間的所有食物,並按照標籤進行聚合查詢,代碼如下:
GET food/_search { "query": { "range": { "Price": { "gte": 50, "lte": 500 } } }, "aggs": { "tags_bucket": { "terms": { "field": "Tags.keyword", "order": { "_count": "asc" } } } } }
搜索結果如下:
{ "took" : 5, "timed_out" : false, "_shards" : { "total" : 3, "successful" : 3, "skipped" : 0, "failed" : 0 }, "hits" : { "total" : { "value" : 3, "relation" : "eq" }, "max_score" : 1.0, "hits" : [ { "_index" : "food", "_id" : "5", "_score" : 1.0, "_source" : { "CreateTime" : "2022-07-09 13:11:11", "Desc" : "榴蓮 非常好喫 很貴 喫一個相當於喫一隻老母雞", "Level" : "高級水果", "Name" : "榴蓮", "Price" : 100.11, "Tags" : [ "貴", "水果", "營養" ], "Type" : "水果" } }, { "_index" : "food", "_id" : "3", "_score" : 1.0, "_source" : { "CreateTime" : "2022-06-07 13:11:11", "Desc" : "蘆筍來自國外進口的蔬菜,西餐標配", "Level" : "中等蔬菜", "Name" : "蘆筍", "Price" : 66.11, "Tags" : [ "有點貴", "國外", "綠色蔬菜", "營養價值高" ], "Type" : "蔬菜" } }, { "_index" : "food", "_id" : "6", "_score" : 1.0, "_source" : { "CreateTime" : "2022-07-08 13:11:11", "Desc" : "貓砂王榴蓮 榴蓮中的戰鬥機", "Level" : "高級水果", "Name" : "貓砂王榴蓮", "Price" : 300.11, "Tags" : [ "超級貴", "進口", "水果", "非常好喫" ], "Type" : "水果" } } ] }, "aggregations" : { "tags_bucket" : { "doc_count_error_upper_bound" : 0, "sum_other_doc_count" : 0, "buckets" : [ { "key" : "國外", "doc_count" : 1 }, { "key" : "有點貴", "doc_count" : 1 }, { "key" : "綠色蔬菜", "doc_count" : 1 }, { "key" : "營養", "doc_count" : 1 }, { "key" : "營養價值高", "doc_count" : 1 }, { "key" : "貴", "doc_count" : 1 }, { "key" : "超級貴", "doc_count" : 1 }, { "key" : "進口", "doc_count" : 1 }, { "key" : "非常好喫", "doc_count" : 1 }, { "key" : "水果", "doc_count" : 2 } ] } } }
hits中是按照query查詢的結果集,下面是根據query的結果集進行的聚合查詢.
2、先聚合後查詢(注意這裏不是having語法,而是查詢聚合裏面的詳情) 通過post_filter實現
現在需要查詢價格範圍在50到500之間,按照標籤分組之後,標籤包含營養的記錄數據,代碼如下:
GET food/_search { "query": { "range": { "Price": { "gte": 50, "lte": 500 } } }, "aggs": { "tags_bucket":{ "terms": { "field": "Tags.keyword" } } }, "post_filter": { "term": { "Tags.keyword": "營養" } } }
搜索結果如下:
{ "took" : 41, "timed_out" : false, "_shards" : { "total" : 3, "successful" : 3, "skipped" : 0, "failed" : 0 }, "hits" : { "total" : { "value" : 1, "relation" : "eq" }, "max_score" : 1.0, "hits" : [ { "_index" : "food", "_id" : "5", "_score" : 1.0, "_source" : { "CreateTime" : "2022-07-09 13:11:11", "Desc" : "榴蓮 非常好喫 很貴 喫一個相當於喫一隻老母雞", "Level" : "高級水果", "Name" : "榴蓮", "Price" : 100.11, "Tags" : [ "貴", "水果", "營養" ], "Type" : "水果" } } ] }, "aggregations" : { "tags_bucket" : { "doc_count_error_upper_bound" : 0, "sum_other_doc_count" : 0, "buckets" : [ { "key" : "水果", "doc_count" : 2 }, { "key" : "國外", "doc_count" : 1 }, { "key" : "有點貴", "doc_count" : 1 }, { "key" : "綠色蔬菜", "doc_count" : 1 }, { "key" : "營養", "doc_count" : 1 }, { "key" : "營養價值高", "doc_count" : 1 }, { "key" : "貴", "doc_count" : 1 }, { "key" : "超級貴", "doc_count" : 1 }, { "key" : "進口", "doc_count" : 1 }, { "key" : "非常好喫", "doc_count" : 1 } ] } } }
3、取消查詢條件,嵌套查詢
現在需要統計指定範圍內食品的平均值、最大值等等,最後需要帶上一個所有食品的平均值.這個時候計算所有食品的平均值不能受限於查詢條件,實現方式如下:
GET food/_search { "query": { "range": { "Price": { "gte": 50, "lte": 500 } } }, "aggs": { "price_avg":{ "avg": { "field": "Price" } }, "price_max":{ "max": { "field": "Price" } }, "price_min":{ "min": { "field": "Price" } }, "all_price_avg":{ "global": {}, "aggs": { "price_avg":{ "avg": { "field": "Price" } } } } } }
搜索結果如下:
{ "took" : 6, "timed_out" : false, "_shards" : { "total" : 3, "successful" : 3, "skipped" : 0, "failed" : 0 }, "hits" : { "total" : { "value" : 3, "relation" : "eq" }, "max_score" : 1.0, "hits" : [ { "_index" : "food", "_id" : "5", "_score" : 1.0, "_source" : { "CreateTime" : "2022-07-09 13:11:11", "Desc" : "榴蓮 非常好喫 很貴 喫一個相當於喫一隻老母雞", "Level" : "高級水果", "Name" : "榴蓮", "Price" : 100.11, "Tags" : [ "貴", "水果", "營養" ], "Type" : "水果" } }, { "_index" : "food", "_id" : "3", "_score" : 1.0, "_source" : { "CreateTime" : "2022-06-07 13:11:11", "Desc" : "蘆筍來自國外進口的蔬菜,西餐標配", "Level" : "中等蔬菜", "Name" : "蘆筍", "Price" : 66.11, "Tags" : [ "有點貴", "國外", "綠色蔬菜", "營養價值高" ], "Type" : "蔬菜" } }, { "_index" : "food", "_id" : "6", "_score" : 1.0, "_source" : { "CreateTime" : "2022-07-08 13:11:11", "Desc" : "貓砂王榴蓮 榴蓮中的戰鬥機", "Level" : "高級水果", "Name" : "貓砂王榴蓮", "Price" : 300.11, "Tags" : [ "超級貴", "進口", "水果", "非常好喫" ], "Type" : "水果" } } ] }, "aggregations" : { "all_price_avg" : { "doc_count" : 6, "price_avg" : { "value" : 83.44333092371623 } }, "price_min" : { "value" : 66.11000061035156 }, "price_avg" : { "value" : 155.44332885742188 }, "price_max" : { "value" : 300.1099853515625 } } }
這裏通過 "global": {}來實現取消查詢條件