前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >终于有人把HDFS架构和读写流程讲明白了

终于有人把HDFS架构和读写流程讲明白了

作者头像
IT阅读排行榜
发布2023-02-13 17:57:20
2.7K0
发布2023-02-13 17:57:20
举报
文章被收录于专栏:华章科技

导读:HDFS(Hadoop Distributed File System)是一种分布式文件系统,可运行在廉价的硬件上,能够处理超大文件以及提供流式数据操作。HDFS具有易扩展、高度容错、高吞吐量、高可靠性等特征,是处理大型数据集的强有力的工具。

作者:蒋杰 刘煜宏 陈鹏 郑礼雄 陶阳宇 罗韩梅

来源:大数据DT(ID:hzdashuju)

01 HDFS基础

以下是HDFS设计时的目标。

1. 硬件故障

硬件故障对于HDFS来说应该是常态而非例外。HDFS包含数百或数千台服务器(计算机),每台都存储文件系统的一部分数据。事实上,HDFS存在大量组件并且每个组件具有非平凡的故障概率,这意味着某些组件始终不起作用。因此,检测故障并从中快速自动恢复是HDFS的设计目标。

2. 流式数据访问

在HDFS上运行的应用程序不是通常在通用文件系统上运行的通用应用程序,需要对其数据集进行流式访问。HDFS用于批处理而不用于用户的交互式使用,相对于数据访问的低延迟更注重数据访问的高吞吐量。

可移植操作系统接口(Portable Operating System Interface of UNIX, POSIX)标准设置的一些硬性约束对HDFS来说是不需要的,因此HDFS会调整一些POSIX特性来提高数据吞吐率,事实证明是有效的。

3. 超大数据集

在HDFS上运行的应用程序具有大型数据集。HDFS上的一个文件大小一般在吉字节(GB)到太字节(TB)。因此,HDFS需要设计成支持大文件存储,以提供整体较高的数据传输带宽,能在一个集群里扩展到数百上千个节点。一个HDFS实例需要支撑千万计的文件。

4. 简单的一致性模型

HDFS应用需要“一次写入多次读取”访问模型。假设一个文件经过创建、写入和关闭之后就不会再改变了。这一假设简化了数据一致性问题,并可实现高吞吐量的数据访问。MapReduce应用或网络爬虫应用都非常适合这个模型。将来还需要扩充这个模型,以便支持文件的附加写操作。

5. 移动计算而不是移动数据

当应用程序在其操作的数据附近执行时,计算效率更高。当数据集很大时更是如此,这可以最大限度地减少网络拥塞并提高系统的整体吞吐量。HDFS为应用程序提供了接口,使其自身更靠近数据所在的位置。

6. 跨异构硬件和软件平台的可移植性

HDFS的设计考虑到了异构硬件和软件平台间的可移植性,方便了HDFS作为大规模数据应用平台的推广。

从Hadoop这些年的发展来看,HDFS依靠上述特性,成为不断演进变革的大数据体系的坚实基石。

02 HDFS架构

HDFS是一个典型的主/备(Master/Slave)架构的分布式系统,由一个名字节点Namenode(Master) +多个数据节点Datanode(Slave)组成。其中Namenode提供元数据服务,Datanode提供数据流服务,用户通过HDFS客户端与Namenode和Datanode交互访问文件系统。

如图3-1所示HDFS把文件的数据划分为若干个块(Block),每个Block存放在一组Datanode上,Namenode负责维护文件到Block的命名空间映射以及每个Block到Datanode的数据块映射。

▲图3-1 HDFS架构

HDFS客户端对文件系统进行操作时,如创建、打开、重命名等,Namenode响应请求并对命名空间进行变更,再返回相关数据块映射的Datanode,客户端按照流协议完成数据的读写。

  • HDFS基本概念

HDFS架构比较简单,但涉及概念较多,其中几个重要的概念如下:

1. 块(Block)

Block是HDFS文件系统处理的最小单位,一个文件可以按照Block大小划分为多个Block,不同于Linux文件系统中的数据块,HDFS文件通常是超大文件,因此Block大小一般设置得比较大,默认为128MB。

2. 复制(Replica)

HDFS通过冗余存储来保证数据的完整性,即一个Block会存放在N个Datanode中,HDFS客户端向Namenode申请新Block时,Namenode会根据Block分配策略为该Block分配相应的Datanode replica,这些Datanode组成一个流水线(pipeline),数据依次串行写入,直至Block写入完成。

3. 名字节点(Namenode)

Namenode是HDFS文件系统的管理节点,主要负责维护文件系统的命名空间(Namespace)或文件目录树(Tree)和文件数据块映射(BlockMap),以及对外提供文件服务。

HDFS文件系统遵循POXIS协议标准,与Linux文件系统类似,采用基于Tree的数据结构,以INode作为节点,实现一个目录下多个子目录和文件。INode是一个抽象类,表示File/Directory的层次关系,对于一个文件来说,INodeFile除了包含基本的文件属性信息,也包含对应的Block信息。

数据块映射信息则由BlockMap负责管理,在Datanode的心跳上报中,将向Namenode汇报负责存储的Block列表情况,BlockMap负责维护BlockID到Datanode的映射,以方便文件检索时快速找到Block对应的HDFS位置。

HDFS每一步操作都以FSEditLog的信息记录下来,一旦Namenode发生宕机重启,可以从每一个FSEditLog还原出HDFS操作以恢复整个文件目录树,如果HDFS集群发生过很多变更操作,整个过程将相当漫长。

因此HDFS会定期将Namenode的元数据以FSImage的形式写入文件中,这一操作相当于为HDFS元数据打了一个快照,在恢复时,仅恢复FSImage之后的FSEditLog即可。

由于Namenode在内存中需要存放大量的信息,且恢复过程中集群不可用,HDFS提供HA(主/备Namenode实现故障迁移Failover)以及Federation(多组Namenode提供元数据服务,以挂载表的形式对外提供统一的命名空间)特性以提高稳定性和减少元数据压力。

4. Datanode

Datanode是HDFS文件系统的数据节点,提供基于Block的本地文件读写服务。定期向Namenode发送心跳。Block在本地文件系统中由数据文件及元数据文件组成,前者为数据本身,后者则记录Block长度和校验和(checksum)等信息。扫描或读取数据文件时,HDFS即使运行在廉价的硬件上,也能通过多副本的能力保证数据一致性。

5. FileSystem

HDFS客户端实现了标准的Hadoop FileSystem接口,向上层应用程序提供了各种各样的文件操作接口,在内部使用了DFSClient等对象并封装了较为复杂的交互逻辑,这些逻辑对客户端都是透明的。

03 HDFS读写流程

1. HDFS客户端写流程

图3-2所示为客户端完成HDFS文件写入的主流程。

▲图3-2 客户端完成HDFS写入的主流程

1)创建文件并获得租约

HDFS客户端通过调用DistributedFileSystem# create来实现远程调用Namenode提供的创建文件操作,Namenode在指定的路径下创建一个空的文件并为该客户端创建一个租约(在续约期内,将只能由这一个客户端写数据至该文件),随后将这个操作记录至EditLog(编辑日志)。Namenode返回相应的信息后,客户端将使用这些信息,创建一个标准的Hadoop FSDataOutputStream输出流对象。

2)写入数据

HDFS客户端开始向HdfsData-OutputStream写入数据,由于当前没有可写的Block,DFSOutputStream根据副本数向Namenode申请若干Datanode组成一条流水线来完成数据的写入,如图3-3所示。

▲图3-3 流水线数据写入示意图

3)串行写入数据,直到写完Block

客户端的数据以字节(byte)流的形式写入chunk(以chunk为单位计算checksum(校验和))。若干个chunk组成packet,数据以packet的形式从客户端发送到第一个Datanode,再由第一个Datanode发送数据到第二个Datanode并完成本地写入,以此类推,直到最后一个Datanode写入本地成功,可以从缓存中移除数据包(packet),如图3-4所示。

▲图3-4 串行写入数据示意图

4)重复步骤2和步骤3,然后写数据包和回复数据包,直到数据全部写完。

5)关闭文件并释放租约

客户端执行关闭文件后,HDFS客户端将会在缓存中的数据被发送完成后远程调用Namenode执行文件来关闭操作。

Datanode在定期的心跳上报中,以增量的信息汇报最新完成写入的Block,Namenode则会更新相应的数据块映射以及在新增Block或关闭文件时根据Block映射副本信息判断数据是否可视为完全持久化(满足最小备份因子)。

2. HDFS客户端读流程

相对于HDFS文件写入流程,HDFS读流程相对简单,如图3-5所示。

▲图3-5 HDFS读流程

1)HDFS客户端远程调用Namenode,查询元数据信息,获得这个文件的数据块位置列表,返回封装DFSIntputStream的HdfsDataInputStream输入流对象。

2)客户端选择一台可用Datanode服务器,请求建立输入流。

3)Datanode向输入流中写原始数据和以packet为单位的checksum。

4)客户端接收数据。如遇到异常,跳转至步骤2,直到数据全部读出,而后客户端关闭输入流。当客户端读取时,可能遇到Datanode或Block异常,导致当前读取失败。正由于HDFS的多副本保证,DFSIntputStream将会切换至下一个Datanode进行读取。与HDFS写入类似,通过checksum来保证读取数据的完整性和准确性。

本文摘编自《腾讯大数据构建之道》,经出版方授权发布。(ISBN:978-7-111-71076-9)

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2022-08-18,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 大数据DT 微信公众号,前往查看

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

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
大数据
全栈大数据产品,面向海量数据场景,帮助您 “智理无数,心中有数”!
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档