HDFS概述
HDFS,全称:Hadoop Distributed File System,即Hadoop分布式文件系统,它来源于Google的发布的GFS。
HDFS可将多台机器组合在一起进行数据存储(集群),是整体存储的能力。
HDFS支持无限拓展,比如集群中的容量不够存储了,可以额外加机器,理论上是可以存储无限多的文件。
HDFS推荐存储大文件、不适合存储小文件,原因是:每个文件需要记录对应的元数据(metadata),这些元数据是存放在内存中的,当小文件足够多时,内存会更多的占用。
HDFS一般针对的是历史数据,故适合用来做离线计算和离线存储,由于历史数据一般比较庞大,处理起来比较耗时,所以,我们允许HDFS有一定的延迟,不用做到实时。
所谓元数据,就是记录数据的数据,比如记录数据的大小、类型、存放位置等信息
HDFS架构
上面是HDFS的架构图,从上面图片可以看出HDFS是主从架构。
- NameNode:管理HDFS集群和HDFS所有的元数据,Client要进行上传下载文件,必须通过NameNode,同时,DataNode会定时向NameNode发送自己的磁盘信息和Block信息
- DataNode:存放数据的节点,每隔一段时间会向NameNode报告自己的信息,在Client发起文件上传下载请求时,通过NameNode的“同意”后,Client会与DataNode建立连接。
- SecondaryNameNode:辅助管理元数据,相当于NameNode的“秘书”,定时将NameNode内存中的元数据持久化
HDFS切片
上面有提到Block,在文件上传时,HDFS会将文件以Block进行存储,在3.x版本中,一个Block默认是128M。
Block是一个逻辑单元,与实际文件大小无关,但文件超过128M时,HDFS会将文件进行切片,比如一个大小为300M的文件,上传到HDFS时,会被切分为三块,分别为:
{
"blk1": "128M",
"blk2": "128M",
"blk3": "44M"
}
HDFS副本机制
当我们上传文件到HDFS时候,HDFS会根据配置和节点数,对文件进行复制,也就是多放几个副本,这样的好处是:当文件发生丢失或者损坏时,多个副本也能保证其数据的完整性。当然也有缺点:文件过大,副本存放比较慢。
HDFS默认是3个副本,我们可以通过修改core-site.xml
文件中dfs.replication
参数修改其副本的数量。副本数不能大于其DataNode节点数。
存放3个副本时,有一个机架感知策略:
如图所示,假如客户端在DataNode所在的机架上,它会在所在机架上随机或者根据节点的容量挑选一台主机进行数据的存储,同时,第二个副本会存放于该机架上的另一个节点(随机或者根据节点的容量),与此同时,在另外的机架上(随机),也会随机或者根据节点的容量在对应机架上找一台主机进行存储。
HDFS的读写过程
上传文件可以概述为:
1、客户端向NameNode发起上传请求
2、NameNode进行权限检查是否可以上传文件,如果没问题,将主机列表反馈给客户端
3、客户端将文件进行切片,然后和主机建立通信,分别上传一个个block
4、当所有block上传完毕,客户端向NameNode汇报上传情况,NameNode更新元数据
下载文件可以概述为:
1、客户端NameNode发起下载请求
2、NameNode经过权限检查,如果没问题,向客户端返回文件的block位置信息
3、客户端根据位置信息分别和对应的主机建立通信
4、客户端读取每个block数据并向这些block数据进行拼接,形成完整文件
HDFS元数据辅助管理
由于元数据是存放于内存中的,在集群重新启动或者当NameNode宕机时,内存中的元数据可能存在丢失的风险,此时,我们的SecondaryNameNode就会定时将元数据进行持久化。
图中多了两个新角色:fsimages
和edits
fsimages
装的数据就是元数据本身,edits
则是记录元数据操作的日志。
具体的操作细节:
1、SecondaryNameNode所在节点会定期将NameNode中的edits和fsimages复制到SecondaryNameNode节点中
2、在SecondaryNameNode节点,会将这两个文件进行合并,生成新的文件fsimages.ckpt,并复制到NameNode节点中
3、NameNode中的edits日志文件此刻会生成新的日志文件edits.new,与从SecondaryNameNode到来的fsimages.ckpt结合,生成新的edits和fsimages,开始了新一轮的等待。
所以,假如当NameNode内存中的元数据发生丢失的时候,是可以从NameNode所在节点的edits和fsimages中恢复的。
值得注意的是,当NameNode中的edits和fsimages如果损坏,同时内存中的元数据也还没载入(假设此时HDFS重启),我们还可以从SecondaryNameNode中对数据进行恢复,但是,此刻会发生一个数据丢失的问题。比如:
11点59分数据损坏,NameNode宕机
这时候11点到11点59分的日志文件消失,内存中的数据也恢复不了
此时我们损失的就是这段时间内存入的文件信息