概述:
使用过HDFS的同学都知道,HDFS有垃圾回收站的功能,当你误删除文件的时候,HDFS会把文件存储到你所在用户的垃圾回收站中,想要恢复文件,只需要从垃圾回收站中找回,当然必须在垃圾回收站的指定日期中。这个是正常的操作。
下面我说一个不正常的操作,如果你的垃圾回收站的间隔日期设置的比较大,当你需要执行大量MR任务时候,就会存在很多垃圾日志存储到你的回收站中,这样就占用了系统大量的存储资。为了解决这个问题,于是想到了如果跳过回收站去删除文件不就可以了。接着执行了一下的指令:
hdfs dfs -rm -R -skipTrash **
于是这样就产生了一个问题,人总是会犯错的,如果这个时候误删除了文件该如何处理。
注意:
如果执行了当前的指令,应该立刻关闭当前hadoop集群。已经删除的文件不可以在恢复,我们只能恢复还没有来得及被删除的文件。
疑问:
- 关闭的Hadoop集群能否立刻重启
- 重启会不会接着上次未执行完成的指令接着删除数据
- 重启,如何恢复原数据
带着这些问题,我们有必要去深入的了解下Hadoop集群执行删除指令步骤,才可以找到靠谱的方法去 恢复还未被删除的数据。
HDFS执行删除文件的流程
- 客户端hdfs-client 提交删除任务给NameNode
- NameNode接收到删除任务以后,会把当前执行的命令同步到其执行操作文件Edits中,同时更新当前的Fsimage镜像文件。然后把任务按批量分发给DataNode进行执行
- DataNode接收到任务以后执行删除操作
所以我们能做到的就是第二步到第三步之间的操作,立刻关闭服务器,中断Namenode发送给DataNode的执行命令。
回过头来解答一下前两个疑问:
第一个疑问解答:关闭服务器之后不能立刻重启,重启之后数据依然消失,因为已经产生了新的镜像文件。
第二个疑问解答:由于NameNode在执行命令之前会把执行到指令写到edit中,所以重启之后,会接着之前执行未完成的地方接着执行
所以我们这里得出来结论,只有恢复hdfs删除操作之前的元数据,就能达到对之前数据的修复。但是已经删除的数据是修复不了的,修复之后会抛出数据块缺失异常。为此我们要研究下Edits文件和Fsimage文件在hdfs中的作用,才能知道如何修改恢复。
Edit文件和Fsimage文件的作用
在Hdfs中,每次客户端提交给NameNode的操作都会被记录到edits****的文件中,随着文件的逐渐增加,会把edits里面的所有操作进行合并提取放到Fsimage中。这样NameNode在启动的时候,会加载Fsimage镜像文件刷新到内存中,其实Fsimage文件就是NameNode的MateData的序列化。那么我们就知道了这两个文件的作用:
edits文件:记录操作过程
Fsimage文件:记录当前NameNode的元数据信息
那么根据这两个文件作用,我们可以得出来,我们只需要恢复到被删除之前的Fsimage和edits的话,就可以对hdfs的元数据进行恢复。
为此我们首先找到这个文件的的存储样式:
通过观察我们发现,当前系统中存在两份fsimage文件。而且每个fsimage文件都编号都对应着edtis文件。这样根据文件的时间记录,我们很简单的发现比较老的edits文件。
恢复操作:
- 首先备份当前的这个元数据文件目录,放到比较安全的目录
- 将NameNode元数据目录中最近生成的edit和fsimage给删除了,只保留上一个版本的镜像文件:
- 把NameNode所在节点的edit,fsimage的备份目录文件清空
- 注意这里只启动NameNode节点,不要启动其他任何节点,启动以后观察当前HDFS中是否存在已经删除的文件元数据信息(所对应的文件夹目录)
- 一个一个启动DataNode节点,观察数据的存储情况
- 清空SecnodaryNameNode备份节点的所有元数据,启动该节点
至此,HDFS元数据修复已经完成,所有节点启动以后,由于之前删除了数据,会存在副本看缺失的情况,因为删除的数据已经不存在了。而存在的数据就是还没来得及删除的。提示NameNode进入安全模式,最后强制退出安全模式即可。