目录:

  1. HDFS是什么
  2. HDFS架构
  3. HDFS组件及其作用
  4. HDFS副本放置原则
  5. HDFS读写过程
  6. HDFS优缺点
  7. HDFS常用配置
  8. HDFS常用命令

一、HDFS是什么

1. HADOOP 1.0 中有两个模块

Hadoop分布式文件系统HDFS(Hadoop Distrbuted File System)、分布式计算框架MapReduce。

2. HADOOP 2.0 对HADOOP 1.0进行了改进。

· 增加了资源调度框架Yarn。

将JobTracker的资源管理和任务调度分开,分别由ResourceManager(负责应用程序的资源分配)和ApplicationManager(负责一个应用程序的任务管理)实现;

可为不同应用程序进行资源管理和任务调度,不仅限MapReduce一种框架,还可为Spark、Storm等框架使用

·引入HDFS联邦。

·引入高可用(HA)

hdfs block存放位置 hdfs block 默认保存几份_元数据


·HDFS快照

·HDFS缓存

3. HDFS

将文件按照block大小切割后,形成一些切片文件,同时每个切片文件都有多个副本,这些切片文件分散放在多个服务器上存储,即为hadoop分布式文件系统;

用户不用管文件是什么格式,被分到哪台机器上,只需要执行命令从hdfs上读写

hdfs block存放位置 hdfs block 默认保存几份_hdfs block存放位置_02

4. HDFS核心思想:

分散均匀存储、备份冗余存储。
5. HDFS使用横向拓展(增加机器)来提高存储容量,而不是纵向扩展(提高单个机器的配置)

二、HDFS架构

1. master-slave主从架构。

在HDFS中,主节点master又被称为Namenode节点,从节点slave又被称为Datanode节点。

( 在MapReduce中,主节点master又被称为JobTracker(任务分配与资源管理),从节点slave又被称为TaskTracker(任务执行 )

hdfs block存放位置 hdfs block 默认保存几份_hdfs_03


hdfs block存放位置 hdfs block 默认保存几份_hdfs block存放位置_04

三、HDFS组件及其作用

1. HDFS有3个组件:

namenode, secondarynamenode, datanode

组件

作用

其他

NameNode

1)主节点master(hadoop1.0中只有一个); 2)管理整个文件系统,接收用户请求;3)管理整个文件系统的命名空间(namespace),维护文件系统目录结构;4)存元数据(默认存内存,可持久化到磁盘fsimage以防丢失);5)管理两种映射关系:“文件 → blockid list(一个文件存到哪些block里)” :静态,存磁盘,通过fsimage和edit logs维护“。“blockid → datanode节点(每个block在哪个datanode上)”:动态,不属于元数据,不持久化到磁盘,集群启动自动建立

1)因为只有一个,存在单点故障问题。Namenode无法在内存中加载全部元数据信息时,集群就会崩掉;2)文件系统的block是最基本的存储和操作单位,默认64M(HDFS2.0默认128M),可通过配置修改;3)fsimage:整个文件系统的快照,是某一时刻对某一目录的镜像;4)datanode通过心跳向namenode反馈blockreport(该节点上有哪些block)

Secondary NameNode

1)定期合并namenode上的edit logs(对文件系统的改动)到自己的fsimage ,并拷贝修改后的fsimage到datanode;2)提供一个namenode的检查点用于故障恢复。3)不是namenode的备份!!!不能在namenode挂掉后顶替成为新的namenode

1)启动namenode时会读取fsimage并跟edit logs合并为新的fsiamge;2) namenode启动后把每一次改动存入edit logs;3)实际中namenode很少重启,因此fsimage会很旧,edit logs会很大,一旦namenode所在服务器宕机,会丢失很多修改;4)因此,综上,需要secondarynamenode来定期合并edit logs 到fsimage,以减小edit logs和得到较新的fsimage

DataNode

1)从节点slave(多个机器); 2)存真实数据;3)管理一个映射关系:“block数据块 → 真实数据”;4)数据会存3个副本;5)通过heartbeat心跳机制周期性向namenode汇报block信息;

关于 fsimage 和 edit logs 的图解:

hdfs block存放位置 hdfs block 默认保存几份_hdfs_05


hdfs block存放位置 hdfs block 默认保存几份_hdfs_06

补充:namenode存的元数据是什么
一个文件的元信息是“数据的数据”,namenode保存的元数据种类有:
文件名目录名以及他们的层级关系;
文件目录的所有者及其权限;
每个文件block块的名及文件被分成了哪些block
… …
下图所示,包含了文件名,备份的份数,对应的 block id等。
以文件 part-0 为例,备份数是 2,block id 是 1 和 3,在 Datanodes 中可以找到,id 为 1 的 block 有两个,id 为 3 的 block 有两个,分别存储在不同 Datanode。两个不同 block id 组合起来就是一个完整的名称为 part-0 的文件。

hdfs block存放位置 hdfs block 默认保存几份_元数据_07

部署:

  • local 模式时,NN和 jobtracker 可以在同一台机器,DN 和 tasktracker 在同一台机器;
  • 大集群、实际应用中,NN和 jobtracker分开部署在不同机器,DN 和 tasktracker 在同一台机器;

2. HDFS2.0

·HDFS联邦
多个namenode,每个namenode分管一部分目录,解决横向内存扩展问题
多个namenode共用datanode
·高可用(HA)。
同时启用2个Namenode,一个处于active状态,一个处于standby状态;
Standby NN 是Active NN的备份。Active NN会把日志文件、镜像文件写到Journal Node(JN奇数个,至少3个)中去,Standby NN启动后会加载镜像文件并周期性的从JN中获取日志文件来保持与Active NN的同步;
Datanode (DN)要同时向Standby NN 和Active NN发送心跳;
当Active NN所在服务器宕机时,可启用Standby NN,数据不会发生丢失,解决单点故障
需要引入Zookeeper(ZK)
zookeeper:
1)ZK的作用:协调分布式集群中各个节点工作有序进行,完成故障转移;
2)zookeeper需要单独维护一个集群,一般三五个节点就够了;
3)zk集群有奇数个节点(因为投票选主);

进程名

作用

其他

zookeeper failoverController(ZKFC)

·zookeeper故障切换控制器。·ZKFC进程会在ZK上注册一个临时节点,监控负责的NN健康状态; ·一旦NN挂掉,相应的临时节点消失,则开始选主(申请独占锁);

·和NN在同一台机器 ·本地NN健康,且无其他NN持有独占锁,就会试图获取独占锁,一旦成功则执行failover,成为新的active NN

JournalNodes(JN)

1.目的:让active NN和standby NN保持数据同步(命名空间,文件→ block的映射 ) 2.JN角色有两种选择: 1)NFS(network file system):远程挂载的网络文件系统,需要额外磁盘空间 ;NN1上安装NFS,NN2挂载NN1的远程共享目录,存fsimage和editlog 2)QJM(Quorum Journal Manager):NN写到大多数JN表示写成功;不需额外磁盘;用奇数台机器存edit log

1、NFS是linux操作系统支持的配置,而QJM是HADOOP自身提供的服务,是应用软件级别的配置; 2、2n+1个JN,最多允许挂n个;

hdfs block存放位置 hdfs block 默认保存几份_hdfs_08

  • 以下图片是一个实际生产环境中,HA和HDFS联邦同时部署的例子

部署:

  • Active NN 和 standby NN硬件配置相同;
  • JN 为奇数个且至少3个;
  • HA中由于standby NN也执行namespace的checkpoints,因此不能再运行Secondary NN、CheckpointNode、BackupNode

图中有12个datanode,4个namenode,其中NN-1 与NN-2是主备关系(分管/share目录),NN-3 与NN-4是主备关系(分管/User目录),

hdfs block存放位置 hdfs block 默认保存几份_hdfs_09

四、HDFS副本放置原则

1. HDFS多副本机制(默认3副本,可在配置dfs.replication中修改)
**·**在机架 1 上放置第一个副本;
**·**在另一个机架 2 上放置第二副本;
**·**副本三与副本二放置在同一个机架不同机器上;
**·**如果有更多的副本,则随机选择机架,每个机架的副本数量有个上限值,计算方式通常是:(replicas - 1) / racks + 2

hdfs block存放位置 hdfs block 默认保存几份_元数据_10

  1. 以上副本放置原则好处:
    **·**避免一个机架出故障,导致所有数据丢失;
    **·**同一个机架上的节点通信网络会比不同机架节点通信更好,副本二与副本三放置在同一个机架能够节省带宽;
  2. 副本放置原则要开启机架感知功能。
    该功能默认关闭,在core-site.xml文件中配置 net.topology.script.file.name(或者namenode上的hadoop-site.xml中的 topology.script.file.name)
    该配置的值是一个脚本的路径,该脚本接受一个参数(通常为datanode的ip地址),输出一个值(该datanode所在机架位置)。默认值为 DEFAULT_RACK,即将所有datanode视为同一个机架上,但实际可能在不同机架,此时HDFS并不知道每个datanode对应的真是机架,就会将副本随机写到datanode上,不一定满足上述副本放置策略

五、HDFS读写过程

“就近原则”读写。

·“就近”是指:优先顺序为: 同一机架上的datanode > 同数据中心不同机架上的datanode > 不同数据中心的datanode

**·**读文件时,读最近的机器上的数据;

**·**写文件时,先写到最近的机器上,再由该机器拷贝到其他两台机器。

距离计算方法。

Hadoop把机器之间的拓扑结构组织成树状结构,并且用到达公共父节点所需跳转次数之和作为距离。以下例子简单说明了距离计算方法:

hdfs block存放位置 hdfs block 默认保存几份_元数据_11


hdfs block存放位置 hdfs block 默认保存几份_HDFS_12

读文件过程:

  1. Client 向 NameNode 发起请求获取文件数据块位置信息
  2. Client 按照数据块距 Client 的远近依次进行连接然后读取数据

写文件过程:

  1. Client 向 NameNode 发起写文件的请求获得可写的 DataNode 列表等信息
  2. Client 根据 HDFS 设定的block大小对文件进行分块
  3. Client 和 NameNode 分配的 DataNode 构成 pipeline 并进行数据写入
  4. 写入完成之后,NameNode 接收来自 DataNode 的消息进行元数据的更新

六、HDFS优缺点

优点:

  1. 大文件存储,海量数据存储。
  2. 高吞吐量
  3. 流式文件访问。
    一次写入,多次读取(不适合随机写,Hadoop2.0中支持append在文件尾部追加),保证数据一致性。
  4. 高容错。
    ·数据完整性校验,数据传输过程中需要校验几次:
    1)client给datanode写数据:要针对写的数据,每个检查单元(512字节)创建一个单独的校验码(crc32),数据和校验码统一发送给Datanode
    2)Datanode接收数据的时候:用同样的加密算法,生成校验码,并校验。在后台还会运行一个扫描进程:DataBlockScanne一旦检测出现问题,通过心跳,通知NN让DN进行修复(拷贝没有问题的备份)
    ·心跳机制。
    datanode通过心跳向namenode反馈本节点状态以及blockreport。blockreport上包含了该datanode上的block列表;
    心跳机制也是检测datanode是否存活的依据(心跳默认3秒发一次,若10分钟namenode收不到datanode的心跳则认为该节点已宕机,不再与该节点发送读写操作);
    ·多副本机制,副本丢失后自动恢复。数据会默认存3个副本
    ·快照fsiamge利于备份与恢复
  5. 低成本

缺点:

  1. 不适合存取大量小文件
    这里的小文件是指远小于block大小的文件;
    小文件的寻址时间会超过读取时间,违反HDFS设计初衷;
    文件会按照block大小被切分成不同数据块,小文件无论多小都会独立保存为一个block,而block信息则是保存在元数据中的。namenode存储元数据信息(一个数据块的元数据大小大约150byte),一旦小文件过多会导致元数据过多,导致用大量内存或磁盘来存储很小的文件;
    eg. 有100个1M的文件存储进入HDFS系统,那么数据块的个数就是100个,元数据的大小就是100*150byte,消耗了15000byte的内存,但是只存储了100M的数据
    有1个100M的文件存储进入HDFS系统,那么数据块的个数就是1个,元数据的大小就是150byte,消耗量150byte的内存,存储量100M的数据。
  2. 不适合随机读写
  3. 不支持并发写入
  4. 不支持文件修改。
    只能先从HDFS上删除,再重新上传新的文件以达到修改的目的。(Hadoop2.0中支持append在文件尾部追加)
  5. 不适合低延迟访问。
    如不适合毫秒级读写

七、HDFS常用配置

从运维角度,HDFS需要了解以下配置参数

文件

参数配置

说明

hdfs-site.xml

dfs.replication

1)每个block的副本份数;2)默认值:3

dfs.data.dir

1)datanode在本地磁盘存放block的位置;2)默认值:${hadoop.tmp.dir}/dfs/data

dfs.name.dir

namenode元数据存放位置;默认值: hadoop.tmp.dir/dfs/name

dfs.namenode.handler.count

namenode用来处理来自datanode的RPC请求的线程数量;建议设置为datanode数量的10%,一般在10~200个之间;太小会在datanode传输数据时日志中报告“connection refused”信息;在namenode上设置;默认值:10;

dfs.datanode.handler.count

datanode用来连接namenode的RPC请求的线程数量;太小会导致性能下降甚至报错;在datanode上设置;默认值:3

core-site.xml

fs.checkpoint.dir

secondary NN 用来存储checkpoint image文件;以逗号分隔的文件夹列表;secondary NN 上设定;默认值:${hadoop.tmp.dir}/dfs/namedecondary

hadoop.tmp.dir

HDFS与本地磁盘的临时文件;默认值:/tmp/hadoop-${user.name};需要在所有节点种设置

fs.trash.interval

文件被删除放入用户目录下的.Trash目录下,经过此参数设置的分钟数后删除数据;默认值0,即禁用trash功能,建议修改成1440(一天);

八、HDFS常用命令

注:以下 “hdfs dfs”,“hadoop dfs”,二者均只能操作HDFS文件系统,一般用前者,后者被弃用;
“hadoop fs” 可以操作任何文件系统

因此,以下出现的 “hdfs dfs” 均可替换成 “hadoop fs”

功能

命令

举例

其他

查看hdfs有哪些指令及参数,help命令

hdfs dfs

上传本地文件到hdfs,put命令

hdfs dfs -put 文件路径 目录名

hdfs dfs -put test.txt /user/hzy #把本地文件test.txt上传到hdfs的/user/hzy目录下

如果存在,可以用-f 覆盖:hdfs dfs -put -f test.txt /user/hzy

上传本地文件到hdfs,也可用copyFromLocal命令

hdfs dfs -copyFromLocal 文件路径 目录名

hdfs dfs -copyFromLocal test.txt /user/hzy

与put命令用法相同

创建文件夹,mkdir命令

hdfs dfs -mkdir 目录名

hdfs dfs -mkdir /user/hzy/test #在/user/hzy目录下创建test文件夹

删除文件/文件夹,rm命令

hdfs dfs -rm 文件路径/目录名

hdfs dfs -rm /user/hzy/test.txt #删除hdfs上/user/hzy目录下的test.txt 文件;hdfs dfs -rm /user/hzy/test #删除hdfs上/user/hzy目录下的文件夹test(这里test必须为空)

若删除的目录不为空,要加上 -r 级联删除:hdfs dfs -rm -r /user/hzy/test

复制hdfs上的文件到hdfs其他目录,cp命令

hdfs dfs -cp 文件路径 目录名

hdfs dfs -cp /user/temp/test.txt /user/hzy #复制/user/temp目录下的test.txt文件到/user/hzy目录

将hdfs上的文件移动到hdfs其他目录,mv命令

hdfs dfs -mv 文件路径 目录名

hdfs dfs -mv /user/temp/test.txt /user/hzy #将/user/temp目录下的test.txt文件移动到/user/hzy目录

查找文件位置,find命令

hdfs dfs -find 目录名 -name 文件名

hdfs dfs -find / -name test.txt #在根目录下查找名为test.txt的文件,区分大小写;hdfs dfs -find / -iname test.txt #在根目录下查找名为test.txt的文件,不区分大小写

也可用:hdfs dfs -ls -R

查看文件/文件夹大小,du命令

hdfs dfs -du 文件路径/目录名

hdfs dfs -du /user/hzy #查看/user/hzy大小

-h不按字节显示大小,带单位:hdfs dfs -du -h /user/hzy

查看文件内容,cat命令

hdfs dfs -cat /user/hzy/test.txt

hdfs dfs -cat /user/hzy/test.txt #查看hdfs上/user/hzy目录下的test.txt 文件内容

常与head、tail、wc等搭配使用。eg.查看前10行:hdfs dfs -cat /user/hzy/test.txt

查看目录下有哪些文件或目录,ls命令

hdfs dfs -ls 目录名

hdfs dfs -ls /usr #查看usr目录

递归显示子目录下的文件加上-R:HDFS dfs -ls -R /user/hzy

查看目录磁盘空间情况,df命令

hdfs dfs -df 目录名

hdfs dfs -df / #查看根目录磁盘空间

获取hdfs上的文件到本地,get命令

hdfs dfs -get 文件路径 目录名

hdfs dfs -get /user/hzy/test.txt . #获取hdfs上/user/hzy目录下的test.txt 文件到本地当前目录

合并获取hdfs上的文件夹的内容到本地,getmerge命令

hdfs dfs -getmerge 文件夹名 本地路径

hdfs dfs -getmerge /hzy . #将hdfs上/hzy目录下的所有明文文件内容合并保存到本地当前路径,并在本地当前路径创建文件hzy保存合并后的文件内容

getmerge可以直接读取明文,将文件夹下明文文件合并

合并获取hdfs上的文件夹的内容到本地,text命令

hdfs dfs -text 目录名/* > 本地文件名

hdfs dfs -text /hzy/* ./hzy.txt #将hdfs上/hzy目录下的所有明文文件内容合并保存到本地当前路径下的hzy.txt 文件

text也可直接读取明文,但效率比getmerge慢

获取hdfs上的文件到本地,也可用copyToLocal命令

hdfs dfs -copyToLocal 文件路径

hdfs dfs -copyToLocal /user/hzy/test.txt

与get命令用法相同

参考:https://cshihong.github.io/2018/05/10/HDFS%E6%8A%80%E6%9C%AF%E5%8E%9F%E7%90%86/