我这样问是因为我们的搜索功能处于流动状态,正在解决问题。但是每次我们更改索引(更改分词器或过滤器,或分片/副本数量),我们都必须删除整个索引并重新将所有Rails模型重新索引到Elasticsearch中……这意味着我们必须考虑停机时间来重新索引所有记录。
我不知道是否有更聪明的方法可以做到这一点?
我这样问是因为我们的搜索功能处于流动状态,正在解决问题。但是每次我们更改索引(更改分词器或过滤器,或分片/副本数量),我们都必须删除整个索引并重新将所有Rails模型重新索引到Elasticsearch中……这意味着我们必须考虑停机时间来重新索引所有记录。
我不知道是否有更聪明的方法可以做到这一点?
我认为@karmi说得对,但让我用更简单的方式解释一下。我需要偶尔通过添加一些新属性或分析设置来升级生产架构。
最近,我开始使用下面描述的场景进行实时、持续负载、零停机索引迁移。您可以远程执行此操作。
以下是步骤:
real1
和别名real_write
、real_read
指向它,real_write
并仅从real_read
读取,_source
文档属性可用。创建带有新映射和您选择的设置的real2
索引。
使用以下批量查询切换写别名。
curl -XPOST 'http://esserver:9200/_aliases' -d '
{
"actions" : [
{ "remove" : { "index" : "real1", "alias" : "real_write" } },
{ "add" : { "index" : "real2", "alias" : "real_write" } }
]
}'
这是原子操作。从此时起,real2
将在所有节点上填充新客户端数据。阅读器仍通过 real_read
使用旧的 real1
。这是最终一致性。
必须将数据从 real1
迁移到 real2
,但不能用旧条目覆盖 real2
中的新文档。迁移脚本应使用 bulk
API 和 create
操作(而非 index
或 update
)。我使用简单的 Ruby 脚本 es-reindex,它具有良好的预计完成时间状态:
$ ruby es-reindex.rb http://esserver:9200/real1 http://esserver:9200/real2
更新于2017年您可以考虑使用新的重新索引API,而不是使用脚本。它有很多有趣的功能,比如冲突报告等。
现在real2
已经更新并且客户端正在向其写入数据,但他们仍然从real1
中读取数据。让我们更新读取别名:
curl -XPOST 'http://esserver:9200/_aliases' -d '
{
"actions" : [
{ "remove" : { "index" : "real1", "alias" : "real_read" } },
{ "add" : { "index" : "real2", "alias" : "real_read" } }
]
}'
写入和读取操作使用real2
。您可以备份并从ES集群中删除real1
索引。
完成!
是的,有更聪明的方法可以在不停机的情况下重新索引您的数据。
首先,永远不要使用“最终”索引名称作为真实的索引名称。因此,如果您想将索引命名为“文章”,请不要使用该名称作为物理索引,而是创建一个索引,例如“articles-2012-12-12”或“articles-A”、“articles-1”等。
其次,创建一个名为“alias”的别名指向该索引。然后,您的应用程序将使用这个别名,因此您永远不需要手动更改索引名称、重新启动应用程序等。
第三,在您想要或需要重新索引数据时,将它们重新索引到一个不同的索引中,比如说“articles-B”——Tire的索引工具链中的所有工具都支持您在这里。
完成后,将别名指向新索引。通过这种方式,您不仅可以最小化停机时间(没有任何停机时间),还可以获得一个安全的快照:如果您在新索引中进行索引时出现了问题,您可以切换回旧索引,直到解决问题为止。
我最近写了一篇博客文章,介绍了如何在没有停机的情况下进行重新索引。需要花费一些时间来确定需要做好的各种小事情。希望这能对你有所帮助!
https://summera.github.io/infrastructure/2016/07/04/reindexing-elasticsearch.html
总结:
使用新映射创建新索引。这可以在Elasticsearch的同一实例上或全新实例上完成。
在重新索引期间,您需要让新旧两个索引保持最新状态。对于写操作,可以将写操作发送到新旧两个索引的后台工作程序中。
删除操作有些棘手,因为在删除记录并重新索引到新索引之间存在竞争条件。因此,在重新索引期间,您需要跟踪需要删除的记录,并在完成后处理这些记录。如果您没有执行太多删除操作,则另一种方法是在重新索引期间消除删除的可能性。