我有一个SQL表,正在导出到Elasticsearch。
其中一列是可为null的数字字段,某些记录中有null。
当我们试图对表进行索引时,我们会得到以下错误:
Table:MLS的ETL(BigQuery->ElasticSearch(作业之一具有是索引20000中10000的ES失败区块,可能是由于不兼容的对象。
Failing BigQuery Table: MLS Stack Trace of the error: Traceback (most recent call last): File "/Users/asif/zodiacbackend/zodiacbackend/tasks.py", line 205, in
insertIntoES helper.bulk(es,doc_generator(dataframe,table((文件"Users/asif/zodiabackend/env/lib/python3.7/site packages/elasticsearch/helpers/actions.py";,行300,批量用于ok,streaming_bulk中的项目(客户端,动作,*args、**kwargs(:文件"Users/asif/zodiabackend/env/lib/python3.7/site packages/elasticsearch/helpers/actions.py";,streaming_bulk**kwargs文件中的第230行"Users/asif/zodiabackend/env/lib/python3.7/site packages/elasticsearch/helpers/actions.py";,第158行,在_process_bulk_chunk中引发BulkIndexError("%i个文档(未能建立索引"%len(错误(,错误(elasticsearch.helpers.errors.BulkIndexError:('2个文档未能索引',[{'index':{'_index':'mls','_type':'ml,'_id':"b100qHABEFI45Lp-z3Om","状态":400,"错误":{"类型":"非法_参数_异常","原因":"的映射程序[Lot_Size_Sq_Ft]不同类型,current_type[text],merged_type[long]'},'data':{"Lot_Size_Sq_Ft":十进制('13504'(}}](
如何让系统识别null?
用户WittyID,错过了一些重要的东西,比如:
null_value
的值必须与您的字段具有相同的数据类型,因此在他的示例中,他声明了integer
字段,但将NULL
定义为null_values
,将抛出json_parse_exception
,这在官方链接中被称为important
,如下所示:
null_value需要与字段的数据类型相同。对于例如,长字段不能具有字符串null_value。
null_value
只影响数据的索引方式,它不会修改源文档,因此在源文档中,您传递的任何内容都将被存储,而不是null_values
param中提到的内容,在查询时还需要使用值null_value
param
简而言之,在ES中无法识别null
,因此您可以为null
定义自定义值,然后使用它来索引和查询null
值。使用下面的例子很容易解释整个事情,任何人都可以尝试:
创建索引
{
"mappings": {
"properties": {
"my_signed_integer": {
"type":"integer",
"null_value": -1 --> note we defining `null` values as `-1`.
}
}
}
}
索引文档
存储
null
整数文档{"my_number":null}
如果您从ES获得此文档,它将返回如下:
{
"_index": "so-6053847",
"_type": "_doc",
"_id": "1",
"_version": 1,
"_seq_no": 0,
"_primary_term": 1,
"found": true,
"_source": {
"my_number": null. --> As explained earlier, in source its stored as `null`.
}
}
索引非负值
{"my_number":10}
搜索查询以获取具有null
值的整数
{
"query": {
"term": {
"my_signed_integer": -1 -->notice same `null_value`, you need to mention
}
}
}
结果:
"hits": [
{
"_index": "so-6053847",
"_type": "_doc",
"_id": "1",
"_score": 1.0,
"_source": {
"my_signed_integer": null --> notice it shows `null`, not `-1`
}
}
]
搜索查询其他数字(不为空(,即在我们的案例中为10
{
"query": {
"term": {
"my_signed_integer": 10
}
}
}
结果
"hits": [
{
"_index": "so-6053847",
"_type": "_doc",
"_id": "2",
"_score": 1.0,
"_source": {
"my_signed_integer": 10 -->source matches the indexed value for this doc
}
}
]
您正在处理一个常见的ES头痛问题。Elasticsearch不索引null值(不仅仅是数值null(。您需要在索引映射中指定希望如何对任何检测到的null值进行索引。类似这样的东西:
"mappings": {
"properties": {
"nullable_numeric": {
"type": "integer",
"null_value": -1
},
"nullable_text": {
"type": "text",
"null_value": "NULL"
}
}
一旦你做到了这一点,ES就会知道如何正确地索引这些字段。注意,您不需要更改原始数据,只需让ES知道如何为搜索创建null索引。。。。顺便说一句,当你查询ES.时,它不会影响文档