如何计算元数据并将其添加到现有 Elasticsearch 索引?
How do I compute and add meta data to an existing Elasticsearch index?
我将超过 3800 万个文档(文本字符串)加载到本地计算机上的 Elasticsearch 索引中。我想计算每个字符串的长度并将该值作为元数据添加到索引中。
我是否应该在将文档加载到 Elasticsearch 之前计算字符串长度作为元数据?或者,我可以在事后用计算值更新元数据吗?
我对 Elasticsearch/Kibana 比较陌生,这些问题的出现是由于以下 Python 实验:
作为字符串列表的数据
mylist = ['string_1', 'string_2',..., 'string_N']
L = [len(s) for s in mylist] # this computation takes about 1 minute on my machine
选项 1 的缺点是我没有利用 Elasticsearch,'mylist' 占用了大量内存。
作为 Elasticsearch 索引的数据,其中 'mylist' 中的每个字符串都加载到字段 'text'。
from haystack.document_store.elasticsearch import ElasticsearchDocumentStore
document_store = ElasticsearchDocumentStore(host='localhost', username='', password='', index='myindex')
docs = document_store.get_all_documents_generator()
L = [len(d.text) for d in docs] # this computation takes about 6 minutes on my machine
选项 2 的缺点是计算时间更长。好处是 generator() 释放了内存。计算时间长是我认为将字符串长度(和其他分析)存储为 Elasticsearch 中的元数据的原因。
还有其他我应该考虑的选择吗?我错过了什么?
如果要存储整个文档的大小,我建议安装mapper-size
plugin,它将源文档的大小存储在_size
字段。
如果您只想存储源文档的特定字段的大小,那么您需要进行不同的操作。
我的建议是创建一个 ingest pipeline 来在每个文档被索引之前对其进行处理。然后可以在第一次索引文档时或加载文档后使用该摄取管道。我会告诉你怎么做。
首先,使用 script
processor 创建摄取管道,它将在另一个名为 textLength
.
的字段中的 text
字段中存储字符串的大小
PUT _ingest/pipeline/string-length
{
"description": "My optional pipeline description",
"processors": [
{
"script": {
"source": "ctx.textLength = ctx.text.length()"
}
}
]
}
所以,如果您已经将文档加载到 Elasticsearch 中,并且想用每个文档的其中一个字段的长度来丰富每个文档,您可以在事后使用 Update by Query API ,像这样:
POST myindex/_update_by_query?pipeline=string-length&wait_for_completion=false
当文档第一次被索引时,也可以在索引时利用该摄取管道,只需在索引查询中引用该管道,如下所示:
PUT myindex/_doc/123?pipeline=string-length
这两个选项都可以,请尝试一下并选择最适合您需要的选项。
我将超过 3800 万个文档(文本字符串)加载到本地计算机上的 Elasticsearch 索引中。我想计算每个字符串的长度并将该值作为元数据添加到索引中。
我是否应该在将文档加载到 Elasticsearch 之前计算字符串长度作为元数据?或者,我可以在事后用计算值更新元数据吗?
我对 Elasticsearch/Kibana 比较陌生,这些问题的出现是由于以下 Python 实验:
作为字符串列表的数据
mylist = ['string_1', 'string_2',..., 'string_N'] L = [len(s) for s in mylist] # this computation takes about 1 minute on my machine
选项 1 的缺点是我没有利用 Elasticsearch,'mylist' 占用了大量内存。
作为 Elasticsearch 索引的数据,其中 'mylist' 中的每个字符串都加载到字段 'text'。
from haystack.document_store.elasticsearch import ElasticsearchDocumentStore document_store = ElasticsearchDocumentStore(host='localhost', username='', password='', index='myindex') docs = document_store.get_all_documents_generator() L = [len(d.text) for d in docs] # this computation takes about 6 minutes on my machine
选项 2 的缺点是计算时间更长。好处是 generator() 释放了内存。计算时间长是我认为将字符串长度(和其他分析)存储为 Elasticsearch 中的元数据的原因。
还有其他我应该考虑的选择吗?我错过了什么?
如果要存储整个文档的大小,我建议安装mapper-size
plugin,它将源文档的大小存储在_size
字段。
如果您只想存储源文档的特定字段的大小,那么您需要进行不同的操作。
我的建议是创建一个 ingest pipeline 来在每个文档被索引之前对其进行处理。然后可以在第一次索引文档时或加载文档后使用该摄取管道。我会告诉你怎么做。
首先,使用 script
processor 创建摄取管道,它将在另一个名为 textLength
.
text
字段中存储字符串的大小
PUT _ingest/pipeline/string-length
{
"description": "My optional pipeline description",
"processors": [
{
"script": {
"source": "ctx.textLength = ctx.text.length()"
}
}
]
}
所以,如果您已经将文档加载到 Elasticsearch 中,并且想用每个文档的其中一个字段的长度来丰富每个文档,您可以在事后使用 Update by Query API ,像这样:
POST myindex/_update_by_query?pipeline=string-length&wait_for_completion=false
当文档第一次被索引时,也可以在索引时利用该摄取管道,只需在索引查询中引用该管道,如下所示:
PUT myindex/_doc/123?pipeline=string-length
这两个选项都可以,请尝试一下并选择最适合您需要的选项。