Elasticsearch5.X聚合操作异常:Fielddata is disabled on text fields by default. Set fielddata=true on [color] in order to load
fielddata in memory by uninverting the inverted index. Note that this can however use significant memory.
Fielddata默认情况下禁用文本字段,因为Fielddata可以消耗大量的堆空间,特别是在加载高基数text字段时。一旦fielddata被加载到堆中,它将在该段的生命周期中保持在那里。此外,加载fielddata是一个昂贵的过程,可以导致用户体验延迟命中。处理以上bug可以参考如下方式:
1、可以使用使用该my_field.keyword字段进行聚合,排序或脚本
2、启用fielddata(不建议使用)
Fielddata说明
大多数字段默认为索引,这使得他们可以搜索。但是,排序,聚合和访问脚本中的字段值需要与搜索不同的访问模式。
搜索需要回答这个问题:“哪些文件包含这个术语?” ,而排序和聚合需要回答一个不同的问题:“ 这个文档对这个文档有什么价值?” 。
大多数字段可以使用索引时间,磁盘上doc_values
的这种数据访问模式,但text
字段不支持doc_values
。
相反,text
字段使用名为“查询时内存”的数据结构 fielddata
。这种数据结构是在第一次使用字段用于聚合,排序或脚本时构建的。它是通过从磁盘读取每个段的全部倒排索引来构建的,反转术语??文档关系,并将结果存储在内存中,存储在JVM堆中。
Fielddata在text
默认编辑的字段上被禁用
Fielddata可以消耗大量的堆空间,特别是在加载高基数text
字段时。一旦fielddata被加载到堆中,它将在该段的生命周期中保持在那里。此外,加载fielddata是一个昂贵的过程,可以导致用户体验延迟命中。这就是为什么fielddata默认是禁用的。
如果您尝试对text
字段上的脚本进行排序,聚合或访问值,则会看到以下异常:
Fielddata默认情况下禁用文本字段。
fielddata=true
在[your_field_name
] 上设置,以便通过取消倒置索引来加载内存中的fielddata。请注意,这可以使用大量的内存。
在启用fielddata 编辑之前
在启用fielddata之前,请考虑为什么要使用text
字段进行聚合,排序或在脚本中。这样做通常没有意义。
在索引之前分析文本字段,以便New York
通过搜索new
或搜索可以找到类似的值 york
。terms
这个字段上的聚合将返回一个new
桶和一个york
桶,当你可能想要一个桶调用New York
。
相反,您应该有一个text
用于全文搜索的字段,以及一个 启用了聚合的未分析keyword
字段doc_values
,如下所示:
PUT my_index { “mappings”:{ “my_type”:{ “properties”:{ “my_field”:{ “type”:“text”,“fields”:{ “keyword”:{ “type”:“keyword” } } } } } } }
使用该 |
|
使用该 |
在text
字段上启用fielddata编辑
您可以text
使用PUT映射API在现有字段 上启用fielddata ,如下所示:
PUT my_index / _mapping / my_type { “properties”:{ “my_field”:{ “type”:“text”,“fielddata”:true } } }
您指定的映射 |
该fielddata.*
参数必须在同一指数的同名字段相同的设置。其值可以使用PUT映射API在现有字段上更新。
-
String index =
"cars";
-
String type =
"transactions";
-
SearchRequestBuilder searchRequestBuilder = client.prepareSearch(index).setTypes(type);
-
TermsAggregationBuilder field = AggregationBuilders.terms(
"popular_colors").field(
"color.keyword");
-
searchRequestBuilder.addAggregation(field);
-
searchRequestBuilder.setSize(
0);
-
SearchResponse searchResponse = searchRequestBuilder.execute().actionGet();
-
System.out.println(searchResponse.toString());
参考地址: https://www.elastic.co/guide/en/elasticsearch/reference/current/fielddata.html#field-data-filtering