3.2 HDFS体系结构

HDFS采用master/slave的架构来存储数据,这种架构主要由4个部分组成,分别为HDFS Client、NameNode、DataNode和Secondary NameNode。下面分别介绍这4个组成部分及其功能。

(1)Client—客户端

1)文件切分。文件上传HDFS的时候,Client将文件切分成一个一个的Block,然后进行存储。

2)与NameNode交互,获取文件的位置信息。

3)与DataNode交互,读取或者写入数据。

4)Client提供一些命令来管理HDFS,比如启动或者关闭HDFS。

5)Client可以通过一些命令来访问HDFS。

(2)NameNode—master是一个主管

1)管理HDFS的名称空间。

2)管理数据块(Block)映射信息。

3)配置副本策略。

4)处理客户端读写请求。

(3)DataNode-slave(NameNode下达命令,DataNode执行实际的操作)

1)存储实际的数据块。

2)执行数据块的读/写操作。

(4)Secondary NameNode

并非NameNode的热备。当NameNode挂掉的时候,它并不能马上替换NameNode并提供服务。

1)辅助NameNode,分担其工作量。

2)定期合并fsimage和fsedits,并推送给NameNode。

3)在紧急情况下,可辅助恢复NameNode。

HDFS总体架构为主从结构,主节点只有一个(NameNode),从节点有很多个(DataNode),采用master-slave模式和NameNode中心服务器(master)来维护文件系统树以及整棵树内的文件目录、负责整个数据集群的管理。DataNode分布在不同的机架上(slave):在客户端或者NameNode的调度下,存储并检索数据块,并且定期向NameNode发送所存储的数据块的列表。客户端与NameNode获取元数据,与DataNode交互获取数据。默认情况下,每个DataNode都保存了三个副本,其中两个保存在同一个机架的两个不同的节点上。另一个副本放在不同机架的节点上。NameNode和DataNode都被设计成可以在普通商用计算机上运行。这些计算机通常运行的是GNU/Linux操作系统。

HDFS采用Java语言开发,因此任何支持Java的机器都可以部署NameNode和DataNode。一个典型的部署场景是集群中的一台机器运行一个NameNode实例,其他机器分别运行一个DataNode实例。当然,并不排除一台机器运行多个DataNode实例的情况。集群中单一的NameNode的设计大大简化了系统的架构。NameNode是所有HDFS元数据的管理者,用户数据永远不会经过NameNode。HDFS总体架构和物理网络环境如图3-6和图3-7所示。

图3-6 HDFS总体架构

图3-7 HDFS物理网络环境

实验一NameNode

1)通过maven下载源代码,查看hdfs-default.xml配置文件。

描述信息为:确定在本地文件系统上的DFS名称节点存储名称表(fsimage)。fsimage的内容会被存储到以逗号分隔的列表的目录中,然后在所有的目录中复制名称表目录,用于冗余。在实际应用中只需要将上述的源代码复制到hdfs-site.xml中,将<value>中的值改为以逗号分隔的列表即可。

注意:逗号后千万不可加空格再写文件。

2)通过源代码信息的查找,寻找dfs.NameNode.name.dir的信息,首先应该找到hadoop.tmp.dir的配置信息,从而寻找到core-site.xml。

3)根据上述分析查找tmp目录及其子目录的详细信息,如图3-8所示。

图3-8 tmp目录及其子目录信息

4)VERSION信息的内容。

显示内容:

例3-2多次格式化NameNode的问题原因解释

(1)启动服务器bin/hdfs oiv-i某个fsimage文件。

(2)查看内容bin/hdfs dfs-ls-R webhdfs。//hdfs格式化会改变命名空间ID,首次格式化时DataNode和NameNode会产生一个相同的namespaceID,然后读取数据即可,如果你重新执行格式化的时候,NameNode的namespaceID改变了,但是DataNode的namespaceID没有改变,两边就不一致了,如果重新启动或进行读写Hadoop就会挂掉。

解决方案:hdfs namenode-format-force进行强制的格式化会同时格式化NameNode和DataNode。

完整的命令为hdfs namenode[-format[-clusterid cid][-force][-nonInteractive]]。

查看NameNode内容:

1)启动服务器bin/hdfs oiv-i某个fsimage文件,如图3-9所示。

图3-9 启动服务器

2)查看内容bin/hdfs dfs-ls-R webhdfs://127.0.0.1:5978/,如图3-10所示。

图3-10 查看内容

3)导出结果bin/hdfs oiv-p XML-itmp/dfs/name/current/fsimage_0000000000000000055-o fsimage.xml。

4)查看edtis内容bin/hdfs oev-i tmp/dfs/name/current/edits_0000000000000000057-0000000000000000186-o edits.xml,如图3-11所示。

图3-11 查看edtis内容

在Hadoop2中,NameNode的50030端口换成8088,新的yarn平台默认是8088,如图3-12所示。也可以通过yarn-site.xml进行如下配置。

图3-12 yarn 8088端口

实验二DataNode

1)HDFS块大小如何设定?

描述信息:新文件的默认块大小(以字节为单位),可以使用以下后缀(不区分大小写)指定大小(例如128k,512m,1g等),包括k(千),m(兆),g(giga),t(tera),p(拍);或提供完整的大小(以128MB为单位的134217728)。

2)如何修改默认的块大小?

只需要修改上述配置文件即可,但是这种方式是全局的修改。64M=67108864,如果想针对文件修改,只要使用命令修改即可:hadoop fs-Ddfs.blocksize=134217728-put./test.txt/test。

修改数据块的测试,如图3-13所示。

图3-13 修改数据块测试

源数据信息如图3-14所示。

图3-14 源数据信息

上传之后在HDFS的配置目录查看,其大小等于19B,而非64MB,如图3-15所示。

图3-15 修改块大小

或者通过浏览器查看,如图3-16和图3-17所示。

图3-16 选择浏览器

图3-17 效果对比

注意:一个文件可以产生多个块,多个文件是不可能成为一个块信息的,为了减轻NameNode的压力,最好的方式就是一个文件一个块。

3)文件块存放路径查看与具体信息解释。

查找DataNode存放数据的位置,配置信息在hdfs-site.xml中,如图3-18所示。

图3-18 配置信息

进入DataNode存放信息的目录查看。

可以查看到元数据的信息以及数据信息,如图3-19所示。

图3-19 元数据信息

注意:可以在本地新建一个文件,上传到HDFS中,查看是否增加了块信息。

副本机制:默认为3。vi hdfs-site.xml可以修改,配置文件对全局生效。

如果想一部分文件副本为3,一部分文件副本为2,同样在命令行执行操作即可,如图3-20和图3-21所示。

图3-20 查看副本

图3-21 副本数修改

HDFS的优缺点总结如下。

1.HDFS的优点

(1)处理超大文件

这里的超大文件通常是指数百MB、甚至数百TB大小的文件。目前在实际应用中,HDFS已经能用来存储管理PB级的数据了。

(2)流式的访问数据

HDFS的设计建立在更多地响应“一次写入、多次读写”任务的基础上。这意味着一个数据集一旦由数据源生成,就会被复制分发到不同的存储节点中,然后响应各种各样的数据分析任务请求。在多数情况下,分析任务都会涉及数据集中的大部分数据,也就是说,对HDFS来说,请求读取整个数据集要比读取一条记录更加高效。

(3)运行于廉价的商用机器集群上

Hadoop设计对硬件需求比较低,只需运行在低廉的商用硬件集群上,而无需运行在昂贵的高可用性机器上。廉价的商用机也就意味着大型集群中出现节点故障情况的概率非常高。这就要求设计HDFS时要充分考虑数据的可靠性、安全性及高可用性。

2.HDFS的缺点

(1)不适合低延迟数据访问

如果要处理一些用户要求时间比较短的低延迟应用请求,则HDFS不适合。HDFS是为了处理大型数据集分析任务的,主要是为达到高的数据吞吐量而设计的,这就可能要求以高延迟作为代价。

改进策略:对于那些有低延时要求的应用程序,HBase是一个更好的选择。通过上层数据管理项目来尽可能地弥补这个不足。在性能上有了很大的提升,它的口号就是实时进行。使用缓存或多master设计可以降低client的数据请求压力,以减少延时。

(2)无法高效存储大量小文件

因为NameNode把文件系统的元数据放置在内存中,所以文件系统所能容纳的文件数目是由NameNode的内存大小来决定的。一般来说,每一个文件、文件夹和Block需要占据150B左右的空间,所以,如果你有100万个文件,每一个占据一个Block,就至少需要300MB内存。当前来说,数百万的文件还是可行的,当扩展到数十亿时,对于当前的硬件水平来说就无法实现了。还有一个问题就是,因为Maptask的数量是由splits来决定的,所以用MapReduce处理大量的小文件时,就会产生过多的Maptask,线程管理开销将会增加作业时间。

举个例子,处理10,000MB的文件,若每个split为1MB,那就会有10,000个Maptask,会有很大的线程开销;若每个split为100MB,则只有100个Maptask,每个Maptask将会有更多的事情做,而线程的管理开销也将减小很多。

改进策略:要想让HDFS能处理好小文件,有以下几种方法。

1)利用SequenceFile、MapFile、Har等方式归档小文件,这个方法的原理就是把小文件归档起来管理,HBase就是基于此的。对于这种方法,如果想找回原来的小文件内容,就必须得知道与归档文件的映射关系。

2)横向扩展,一个Hadoop集群能管理的小文件有限,那就把几个Hadoop集群拖在一个虚拟服务器后面,形成一个大的Hadoop集群。Google也曾经这样做过。

3)多master设计,这个作用显而易见。正在研发中的GFS II也改为分布式多Master设计,还支持master的故障转移,而且Block大小改为1MB,有意要调优处理小文件。

(3)不支持多用户写入及任意修改文件

在HDFS的一个文件中只有一个写入者,而且写操作只能在文件末尾完成,即只能执行追加操作。目前HDFS还不支持多个用户对同一文件的写操作以及在文件任意位置进行修改。