首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >Elasticsearch数据迁移踩坑记:分片故障差点把我搞疯

Elasticsearch数据迁移踩坑记:分片故障差点把我搞疯

原创
作者头像
一只牛博
发布2025-09-14 16:41:27
发布2025-09-14 16:41:27
1.9K0
举报
文章被收录于专栏:debug专栏debug专栏

看似简单的迁移需求

最近需要把一台服务器上的Elasticsearch数据迁移到另一台服务器。我心想这有什么难的?不就是把数据拷贝过去,重新启动就完事了。

结果这个"简单"的迁移任务,差点把我搞疯。

image-20241029150544950
image-20241029150544950

上图就是我的迁移思路:服务器A的ES数据迁移到服务器B。看起来很直接,做起来各种坑。

第一个坑:数据没挂载出来

我原来部署ES的时候图省事,没有做数据挂载。现在要迁移数据,得先把容器里的数据拷贝出来。

数据拷贝

ES的数据默认存在容器的/usr/share/elasticsearch/data目录下,需要先拷贝到宿主机:

代码语言:bash
复制
# 从ES容器拷贝数据到宿主机
docker cp es_container:/usr/share/elasticsearch/data /backup/es_data

然后把这些数据传输到目标服务器。我用的scp:

代码语言:bash
复制
scp -r /backup/es_data user@target_server:/data/elasticsearch/

启动新的ES容器

在目标服务器上,用相同的版本启动ES容器,并挂载数据目录:

代码语言:bash
复制
docker run -d \
  --name elasticsearch \
  -p 9200:9200 \
  -v /data/elasticsearch:/usr/share/elasticsearch/data \
  elasticsearch:7.16.2

重要提醒:版本一定要保持一致!我就是在这里踩了坑,版本不一致导致数据格式不兼容。

第二个坑:权限问题

容器启动后,ES立马报错退出:

代码语言:log
复制
java.lang.IllegalStateException: failed to obtain node locks, tried [[/usr/share/elasticsearch/data]] with lock id [0]; maybe these locations are not writable or multiple nodes were started without increasing [node.max_local_storage_nodes] (was [1])?

看这个错误,明显是权限问题。ES容器里的用户无法访问挂载的数据目录。

解决权限问题

代码语言:bash
复制
# 修改数据目录的所有者和权限
sudo chown -R 1000:1000 /data/elasticsearch
sudo chmod -R 775 /data/elasticsearch

这里的1000:1000是ES容器内部用户的UID和GID。修改完权限后,重新启动容器,这个问题就解决了。

第三个坑:分片故障

权限问题解决后,ES容器能正常启动了,但是查询数据的时候又出问题了:

代码语言:log
复制
ElasticsearchStatusException[Elasticsearch exception [type=search_phase_execution_exception, reason=all shards failed]]

all shards failed?这是什么鬼?

检查集群健康状态

代码语言:bash
复制
curl -X GET "http://127.0.0.1:9200/_cluster/health?pretty"

结果显示:

代码语言:json
复制
{
  "cluster_name" : "docker-cluster",
  "status" : "red",
  "unassigned_shards" : 2,
  "active_shards_percent_as_number" : 89.47
}

status是red,还有2个未分配的分片。这就是导致查询失败的原因。

查看分片详情

代码语言:bash
复制
curl -X GET "http://127.0.0.1:9200/_cat/shards?v&pretty"
image-20241029152328016
image-20241029152328016

从图片可以看到,确实有几个分片的状态是UNASSIGNED,没有分配到节点上。

深入分析分片问题

代码语言:bash
复制
curl -X GET "http://127.0.0.1:9200/_cluster/allocation/explain?pretty" -H 'Content-Type: application/json' -d '{
  "index": "acowbo_new",
  "shard": 0,
  "primary": true
}'

这个命令能告诉你分片为什么没有分配。执行后发现了关键信息:

代码语言:txt
复制
"details" : "failed shard on node: failed to create index, failure IllegalArgumentException[Custom Analyzer [ik_analyzer] failed to find tokenizer under name [ik_smart]]"

找到问题了:自定义分析器ik_analyzer找不到ik_smart分词器!

第四个坑:插件缺失

原来的ES安装了IK分词器插件,但是新的ES容器没有安装,导致索引无法正常创建。

安装缺失的插件

代码语言:bash
复制
# 进入ES容器
docker exec -it elasticsearch /bin/bash

# 安装IK分词器插件(版本要和ES版本匹配)
bin/elasticsearch-plugin install https://github.com/medcl/elasticsearch-analysis-ik/releases/download/v7.16.2/elasticsearch-analysis-ik-7.16.2.zip

安装完插件后,重启ES容器:

代码语言:bash
复制
docker restart elasticsearch

验证修复结果

重启后再次检查集群状态:

代码语言:bash
复制
curl -X GET "http://127.0.0.1:9200/_cluster/health?pretty"

现在status应该变成green了,unassigned_shards也变成0。

查询功能也恢复正常了。

迁移的完整经验

这次ES迁移让我学到了不少东西:

1. 数据迁移要完整

不只是拷贝数据文件,还要考虑:

  • ES版本要完全一致
  • 启动参数要保持一致
  • 插件配置要一模一样

2. 权限配置很关键

Docker容器的用户权限和宿主机不同,数据目录的权限要特别注意:

  • 用户ID要匹配(通常是1000:1000)
  • 权限要足够(775或755)

3. 插件依赖要检查

如果原ES用了自定义插件,新环境必须安装相同版本的插件。缺少插件会导致:

  • 索引无法创建
  • 分片分配失败
  • 查询功能异常

4. 分片故障要系统排查

遇到分片问题,排查顺序应该是:

  1. 检查集群健康状态
  2. 查看分片分配情况
  3. 分析具体的分配失败原因
  4. 针对性解决(权限、插件、配置等)

这次迁移的坑点总结

数据挂载的教训

我原来部署ES图省事,没做数据挂载,这次迁移就吃亏了。要先docker cp把数据拷出来,麻烦得要死。

以后部署ES第一件事就是做数据挂载,省得迁移的时候折腾。

权限问题很容易忽略

从一台服务器拷贝到另一台服务器,文件的所有者和权限都可能变化。ES容器启动的时候,如果没有权限访问数据目录,就会直接报错退出。

记住要用chown -R 1000:1000chmod -R 775修改权限。

插件依赖是大坑

这个是我完全没想到的。原来的ES用了IK分词器,新环境没装,直接导致分片分配失败。

而且插件版本还得和ES版本严格匹配,差一个小版本都可能不兼容。

经验教训

经过这次折腾,我总结了几个经验:

迁移前先看看原环境用了什么插件,记录下来,新环境也要装相同版本的。

版本一定要保持一致,别想着顺便升级个版本什么的,数据迁移的时候风险太大。

迁移完不要急着庆祝,先检查集群状态,确保所有分片都正常,再测试查询功能。

说实话,这次ES迁移比我想象的复杂多了。以前以为就是拷贝数据文件的事,现在才知道涉及这么多细节。

记录下来,希望其他人别像我一样踩这些坑。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 看似简单的迁移需求
  • 第一个坑:数据没挂载出来
    • 数据拷贝
    • 启动新的ES容器
  • 第二个坑:权限问题
    • 解决权限问题
  • 第三个坑:分片故障
    • 检查集群健康状态
    • 查看分片详情
    • 深入分析分片问题
  • 第四个坑:插件缺失
    • 安装缺失的插件
    • 验证修复结果
  • 迁移的完整经验
    • 1. 数据迁移要完整
    • 2. 权限配置很关键
    • 3. 插件依赖要检查
    • 4. 分片故障要系统排查
  • 这次迁移的坑点总结
    • 数据挂载的教训
    • 权限问题很容易忽略
    • 插件依赖是大坑
  • 经验教训
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档