ElasticSearch v7.10:如何获取list类型字段的完整唯一列表?
如何在Elasticsearch 7.10中获取数组字段的完整唯一列表
你当前的terms聚合返回单个元素的唯一值,核心原因是:Elasticsearch默认会将数组字段的每个元素独立拆分并建立倒排索引,terms聚合会针对这些单个元素做分组统计,而非将整个数组作为一个整体处理。
方法1:使用Painless脚本实现数组整体聚合
无需修改索引映射,直接通过脚本提取完整数组作为聚合维度,就能得到你需要的完整唯一列表:
GET /products/_search { "size": 0, "aggs": { "unique_category_lists": { "terms": { "script": { "source": "doc['category'].values", "lang": "painless" }, "size": 1500 } } } }
说明
doc['category'].values会提取文档中category字段的完整数组值,将其作为一个整体参与聚合分组- 这种方式无需调整现有数据,但脚本聚合的性能略低于原生字段聚合,数据量较大时需注意资源消耗
方法2:修改映射添加keyword子字段(性能更优)
如果允许重新索引数据,建议给category字段添加keyword类型子字段,让Elasticsearch将整个数组序列化为字符串存储,从而支持高性能的原生聚合:
1. 更新索引映射
PUT /products/_mapping { "properties": { "category": { "type": "integer", "fields": { "raw": { "type": "keyword" } } } } }
2. 重新索引数据
需要将现有数据重新索引,让category.raw字段生成对应数组的序列化值
3. 执行聚合查询
GET /products/_search { "size": 0, "aggs": { "unique_category_lists": { "terms": { "field": "category.raw", "size": 1500 } } } }
说明
keyword类型字段会完整保留数组的序列化形式,因此terms聚合会以整个数组为单位分组- 这种方式性能远优于脚本聚合,适合数据量较大的场景
内容的提问来源于stack exchange,提问作者Praful Bagai
相关产品推荐
相关产品推荐

