Elasticsearch中如何聚合获取事件类型的出现天数与最后发生时间
Elasticsearch 按事件类型统计发生天数及最后发生时间的聚合方案
你需要直接通过Elasticsearch聚合得到每个event_type对应的事件发生天数和最后一次发生时间,无需二次处理。可以通过以下两种更高效的聚合方案实现:
方案一:结合直方图聚合与桶计数
这种方案基于你原本的直方图思路,通过桶脚本直接获取天数:
{ "size": 0, "query": { ... }, "_source": false, "aggregations": { "events": { "terms": { "field": "event_type" }, "aggs": { "last_occurrence": { "max": { "field": "@timestamp" } }, "daily_buckets": { "date_histogram": { "field": "@timestamp", "calendar_interval": "day", "min_doc_count": 1 } }, "occurrence_days": { "bucket_script": { "buckets_path": { "bucketCount": "daily_buckets._bucket_count" }, "script": "params.bucketCount" } } } } } }
各聚合逻辑说明:
last_occurrence:通过max聚合直接提取@timestamp的最大值,即该事件类型最后一次发生的时间,比从直方图桶中取第一个结果更高效。daily_buckets:按天生成直方图桶,min_doc_count=1确保只保留有事件发生的日期桶。occurrence_days:通过bucket_script获取daily_buckets的桶总数,也就是事件发生的天数。
方案二:用基数聚合统计天数(更简洁)
通过将时间戳格式化为日期字符串,用基数聚合统计唯一日期的数量,无需依赖直方图:
{ "size": 0, "query": { ... }, "_source": false, "aggregations": { "events": { "terms": { "field": "event_type" }, "aggs": { "last_occurrence": { "max": { "field": "@timestamp" } }, "occurrence_days": { "cardinality": { "script": { "source": "doc['@timestamp'].value.format('yyyy-MM-dd')" } } } } } } }
各聚合逻辑说明:
last_occurrence:同样用max聚合获取最后发生时间。occurrence_days:通过脚本将每个时间戳格式化为yyyy-MM-dd的日期字符串,再用cardinality统计唯一字符串的数量,直接得到事件发生的天数。
两种方案都能直接在聚合结果中得到每个event_type对应的occurrence_days(发生天数)和last_occurrence(最后发生时间),无需二次处理。
内容的提问来源于stack exchange,提问作者dcolazin
相关产品推荐
相关产品推荐

