Easticsearch从0学到1之nfs快照备份与恢复

背景

(1)场景1:笔者在之前做晋升答辩的时候,被提到这样一个需求:“ES能不能够在需要的时候,把去年的数据快速加载进来能够查询”。由于,鄙人当时紧张直接回答:“因为用ES我们主要是用于对日志查询和分析的,日志量比较大,保存时间较短;最简单的做法,就是把数据先储存在其他的地方,然后用logstash或其他插件打进ES”。其实解决这个问题还有其他办法,如果不是日志场景,数据量不大,我们完全可以把索引close掉,在需要的时候再把他open,就可以实现快速使索引的数据处于可搜索状态。
(2)场景2:我们的日志保存周期一般都比较短,会有周期性的清理策略。但是最近业务方给我们提需求了,他们需要上一个月的日志。因为当时在HDFS中有原日志文件,所以当时决定从hdfs中读取数据到ES中,当时就一顿的找工具如官方提供的ES-Hadoop,比如Alibaba的DataX,其中官网提供的ES-Hadoop需要需要自己写job,经过实践这两种方法都不太好使。最后决定直接用logstash进行读取原日志文件,因为我们的日志文件,压缩了两层分别为tar.gz和第二层log.gz;所以我们需要先解压然后再用logstash去消费,并且由于当时资源紧张只有一台空闲机器供logstash使用,磁盘只有2T左右若所有压缩包全部解压,磁盘百分之两千不够用,所以只能消费完一个解压包之后再解压一个压缩包;问题来了,我不可能一直去盯着有没有消费完,然后再去手动解压哈,于是自己又写了一个shell脚本实现全自动化。最后也算是完成任务了。
以上两个场景让我意识到一个问题,那就是ES数据的备份问题(当然数据备份不是解决上述场景的唯一方法,但是不失为一个途径)。ES不是一个完全做存储的数据库系统,它的主要应用场景是搜索和数据分析,但是对数据做备份也是有必要的。Elasticsearch的副本只是提高可靠性,但是无法应对灾难性故障,因此备份集群对应对一些灾难性事故也是有重要的意义。

ES集群备份方案

双ES集群(或一个集群划分成两个域)

这里我们只讲双ES集群的:假设cluster1存储近几天的日志,cluster2存储近一个月的日志。
对于cluster2集群的要求,特别要求磁盘足够大,在cluster2中对于不用的索引close掉,避免其占用内存。每天凌晨通过remote reindex的方式,把cluster1中的数据导入到cluster2中。
在这里插入图片描述
前提:需要一个冷备集群
缺点:机器资源成本
测试:目前功能测试已通过,可行。remote reindex的速度,性能方面还未测试。

快照

快照的原理,本文不做过多介绍,想要了解的同学建议阅读《ELASTICSEARCH 源码解析与优化实战》样章-第 13 章 SNAPSHOT 模块分析
使用快照的方式,前提必须要有一个快照仓库。官网给出了以下的仓库类型:

  • 共享文件系统,比如 NAS
  • Amazon S3
  • HDFS (Hadoop 分布式文件系统) ,ES对HDFS 有版本的要求
  • Azure Cloud
    下面我们将重点介绍一下是共享文件的方式进行快照:nfs作为快照仓库,在官网上的介绍并不是特别详细,没有说明如何去搭建一个共享文件的仓库。
    前提:准备一台机器,磁盘大约能容纳大于一个月日志一半的量。
    优点:快照的方式,不用去存储原始数据,并且创建索引的那些元信息也都有保存。
    测试:测通可行,恢复速度较慢。
    共享文件系统支持以下配置
参数简介
location指定了一个已挂载的目的地址
compress是否开启压缩。压缩仅对元数据进行(mapping 及 settings),不对数据文件压缩。默认为 true
chunk_size传输文件时数据被分解为块,此处配置块大小,单位为字节默认为 null(无限块大小)
max_snapshot_bytes_per_sec快照操作时节点间限速值,默认40mb
max_restore_bytes_per_sec从快照恢复时节点间限速值,默认40mb
readonly设置仓库属性为只读。默认为 false

nfs方式快照的备份与恢复的实践过程如下。

实践

软件环境

本次实践的环境是在centos7下,并且在三台机器上安装了Elasticsearch集群,详细如下:
查看 linux版本
cat /etc/redhat-release
CentOS Linux release 7.4.1708 (Core)
Elasticsearch 6.4.0
其中机器158,166,44机器已经安装Elasticsearch。173为空闲的磁盘较大的机器。

 客户端机器
 192.99.71.158     
 192.99.71.166                                       
 192.99.71.44
 服务端机器
 192.99.71.173

nfs仓库搭建

服务端

安装nfs服务

yum install -y nfs-utils

在NFS服务端173机器上,编辑vim /etc/exports文件,添加/data/elasticsearch_back目录配置有哪些权限。

/data/elasticsearch_back *(insecure,rw,no_root_squash,sync)

NFS服务做成开机启动

systemctl enable rpcbind.service 
systemctl enable nfs-server.service

启动NFS相应的服务

systemctl start rpcbind.service 
systemctl start nfs-server.service

确认服务是否启动

rpcinfo -p

创建用户,指定uid和用户组
添加用户组并指定gid

groupadd -g 598 elasticsearch

添加用户

useradd -u 664 -g elasticsearch elasticsearch 

改变目录所属组合用户

chown -R  /data/elasticsearch_back

客户端

查看服务端共享目录

showmount -e 192.99.71.173

返回如下信息

Export list for 192.99.71.173:
/data/elasticsearch_back *

在客户端158,166,44安装相应的服务,并启动

yum install -y nfs-utils 
systemctl enable rpcbind.service 
systemctl start rpcbind.service

分别在客户端机器158,166,44上挂载共享目录,将服务端共享目录挂载在客户端/data/es_data_back这个位置

mount -t nfs 192.90.71.173:/data/elasticsearch_back  /data/es_data_back -o proto=tcp -o nolock

可以用命令**df -h**命令进行验证在这里插入图片描述
注意:
(1)目录/data/es_data_back必须是的所属用户,必须是elastic用户。
(2)在elasticsearch.yml加入如下配置,即快照仓库所在位置。

path.repo: ["/data/es_data_back"]

(3)必须每个节点都要创建path.repo,因为索引的分片,数据是分布式的保存,要想快照到全部数据信息,必须每个节点都创建repo,并挂载到共享目录。

测试nfs是否挂载成功

在机器158,166,44或173的任意一台机器上,切换elastic用户,在/data/es_data_back或173的/data/elasticsearch_back下创建文件test.txt,在其他三台机器都能看到。如果实践失败则有可能是一下原因:

问题

四台机器的elasticsearch用户的uid不一致,gid也不一致,为什么会这样呢?实际上是因为你在其中一台机器创建test.txt文件时,其它机器在共享这个文件时,这个文件的uid和gid也被共享了,虽然你是用elasticsearch用户创建的test.txt文件,但是由于三台机器的elasticsearch用户uid和gid不一致,结果在不同机器上看到的用户和用户组不一致,这样就存在权限问题了,设想一下,你在使用snapshot备份的时候,在一台机器上创建了一个备份,而由于四台机器的用户uid和gid不一样在写入的时候,是不是会发生拒绝访问的问题。所以解决方法就是得确保四台机器的uid一致,gid也一致。
查看用户的GID与UID;cat /etc/passwd,我们会找到下面的一条信息。

elasticsearch:x:664:598:elasticsearch user:/nonexistent:/sbin/nologin

elasticsearch:用户名
x 密码:字符x表示密码被加密保存在/etc/shadow文件中
664用户ID(UID):每个用户必需指定UID。UID 0是保留给root用户的,UID 1~99是保留给其它预定义用户的, UID 100~999是保留给系统用户的
598 组ID(GID):主组ID(保存在/etc/group文件中);
**elasticsearch:**用户ID信息,用户备注信息

解决办法

修改用户UID与GID
如下

 elasticsearch 旧的 UID: 1005
 elasticsearch  新的 UID: 644
 elasticsearch 用户组名字: elasticsearch
 elasticsearch所属组的旧 GID: 2000
 elasticsearch所属组的新 GID: 598

步骤1 修改用户的UID

usermod -u 644 elasticsearch

步骤2 修改组的GID

groupmod -g 598  elasticsearch 

elasticsearch用户的家目录下面的文件属主和属组会在1、2命令执行后自动修改成新的uid、gid对应的属主属组,但是其他文件目录需要手动修改

# find / -user 1005 -exec chown -h elasticsearch  {} \;
# find / -group 2000 -exec chgrp -h elasticsearch  {} \;

这样用户和组的uid、gid就修改好了。可以用id命令进行验证

# ls -l /home/elasticsearch/
# id -u elasticsearch
# id -g elasticsearch
# grep elasticsearch /etc/passwd
# grep elasticsearch /etc/group

再次进行测试应该不会出现问题了

快照与恢复

快照

创建快照仓库my_backup

PUT /_snapshot/my_backup
{
  "type": "fs",
  "settings": {
    "location": "/data/es_data_back/back_up",
    "compress": true
  }
}

创建快照,对指定的两个索引进行快照,其中basiclog-pv_1001500-2019-03-26存储数据415MB

PUT _snapshot/my_backup/snapshot_20190329
{
    "indices": "basiclog-pv_1001500-2019-03-26,basiclog-pv_1001500-2019-03-22"
}

获取快照信息,从下面的返回信息可知,创建快照一共耗费大约7秒

{
  "snapshots": [
    {
      "snapshot": "snapshot_20190329",
      "uuid": "TmebuVW7STKTVWCtnF2Fwg",
      "version_id": 6040099,
      "version": "6.4.0",
      "indices": [
        "basiclog-pv_1001500-2019-03-26",
        "basiclog-pv_1001500-2019-03-22"
      ],
      "include_global_state": true,
      "state": "SUCCESS",
      "start_time": "2019-03-29T03:49:21.775Z",
      "start_time_in_millis": 1553831361775,
      "end_time": "2019-03-29T03:49:28.369Z",
      "end_time_in_millis": 1553831368369,
      "duration_in_millis": 6594,
      "failures": [],
      "shards": {
        "total": 10,
        "failed": 0,
        "successful": 10
      }
    }
  ]
}

做好快照之后,我们可以删除该索引

DELETE basiclog-pv_1001500-2019-03-26

恢复

恢复快照中指定的索引

POST /_snapshot/my_backup/snapshot_20190329/_restore
{
    "indices": "basiclog-pv_1001500-2019-03-26"
}

获取快照恢复详细信息GET basiclog-pv_1001500-2019-03-26/_recovery,大概耗费3秒左右;由于返回的信息太多,就只粘贴出部分信息;其中包含每个分片恢复的详细信息。

{
  "basiclog-pv_1001500-2019-03-26": {
    "shards": [
      {
        "id": 3,
        "type": "SNAPSHOT",
        "stage": "DONE",
        "primary": true,
        "start_time_in_millis": 1553831843645,
        "stop_time_in_millis": 1553831846405,
        "total_time_in_millis": 2759,
        "source": {
          "repository": "my_backup",
          "snapshot": "snapshot_20190329",
          "version": "6.4.0",
          "index": "basiclog-pv_1001500-2019-03-26"
        },
        "target": {
          "id": "Z0MGc4DkRKafvAnK8gJaTA",
          "host": "192.99.71.44",
          "transport_address": "10.90.71.44:9300",
          "ip": "192.99.71.44",
          "name": "bj-sjhl-log-es-test-3.test.xesv5.com"
        },
        "index": {
          "size": {
            "total_in_bytes": 43439670,
            "reused_in_bytes": 0,
            "recovered_in_bytes": 43439670,
            "percent": "100.0%"
          },
          "files": {
            "total": 67,
            "reused": 0,
            "recovered": 67,
            "percent": "100.0%"
          },
          "total_time_in_millis": 2685,
          "source_throttle_time_in_millis": 0,
          "target_throttle_time_in_millis": 0
        },
        "translog": {
          "recovered": 0,
          "total": 0,
          "percent": "100.0%",
          "total_on_start": 0,
          "total_time_in_millis": 56
        },
        "verify_index": {
          "check_index_time_in_millis": 0,
          "total_time_in_millis": 0
        }

跨集群恢复

我们还可以把快照拷贝到其他的地方,在其他集群进行快照恢复。下面是我之前做过的一个测试。
方法一
第一:在目标集群中,建议构建与源集群相同的path.repoelasticsearch.yml中进行配置)
第二步:在目标集群创建和源集群一样的仓库

  Put http://192.99.2.210:9200/_snapshot/my_backup
{
  "type": "fs",
  "settings": {
    "location": "/data_es/backup_es/my_fs_backup",
    "compress": true
  }
}

第三步:在源集群,创建快照
第四步:把快照拷贝到目标集群中,与源集群备份仓库的对应,即把源集群/data_es/backup_es/目录下的my_fs_backup,拷贝到目标集群的/data_es/backup_es/
第五步:快照恢复,与在源集群的恢复方式一样。如下是恢复snapshot_20190329下全部的索引

 POST http://192.99.2.210:9200/ _snapshot/my_backup/snapshot_20190329/_restore

方法二:
第一步、第二步和第三步以及第五步与方法一的步骤一样
第四步:断开源集群与nfs文件的挂载关系,把目标集群的path.repo与服务端nfs建立挂载关系

参考文献

[1] https://mp.csdn.net/mdeditor/88894877
[2] https://www.elastic.co/guide/en/elasticsearch/reference/6.4/modules-snapshots.html
[2] Elasticsearch升级踩坑记之使用snapshot备份数据https://blog.csdn.net/u012062455/article/details/79570996
[3] CentOS6.6 NFS服务的安装与配置详解https://blog.csdn.net/wunianjiumeng/article/details/79067641
[4] 大数据量Elastic数据迁移方法及注意事项https://www.2cto.com/database/201610/557571.html
[5] Elasticsearch索引迁移的四种方式https://blog.csdn.net/laoyang360/article/details/65449407
[6] CentOS7.2 通过nfs设置共享文件夹 https://blog.csdn.net/rznice/article/details/72654826
[7] Elasticsearch:跨集群数据迁移之离线迁移 https://www.imooc.com/article/41844
[8] Linux umount命令 <http://www.runoob.com/linux/linux-comm-umount.html
[9] Linux 安装 Elasticsearch6.4.x 详细步骤以及问题解决方案http://blog.51cto.com/moerjinrong/2310817
[10] https://www.elastic.co/guide/en/elasticsearch/reference/6.5/modules-snapshots.html
[11] Elasticsearch–索引备份与迁移 https://blog.csdn.net/u014431852/article/details/52905821/
[12] elasticsearch快照和恢复https://blog.csdn.net/crazyhacking/article/details/45726683
[13] 修改GID与UIDhttps://blog.csdn.net/train006l/article/details/79007483
[14] https://www.cyberciti.biz/faq/linux-change-user-group-uid-gid-for-all-owned-files/
[15] <https://blog.csdn.net/jackailson/article/details/50993427

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值