HDFS的架构(HDFS architecture)
Namenode:负责管理
DataNode:存储数据
Secondary NameNode:一个Namenode的秘书
当一个客户端client想读取数据时:首先跟namenode打交道,获取一些“元数据”Metadata【存放在内存当中】。
然后namenode要查询它的元数据信息——元数据信息保存在【内存里?掉电就丢失了】内存一份,磁盘一份(磁盘保存了一份镜像)
之后把元数据信息返回给客户端,然后客户端读取相应的数据。
比如要读512M的数据,(4块),依次读取。倘若读取前三块之后,第四块存在别的机器上,可以再去别的地方读取块4【数据就近原则:在哪台机器上读取数据快,离我近,就读哪个,走一次交换机就能达到数据,就不走五次】
还可以进行block块的操作,进行一些水平的复制
当一个客户端client想写数据时:写的时候还会复制副本。(见上节)
元数据的存储细节:内存一份,磁盘一份。
namenode里有什么?(根下文件Filename,副本3,被切分成了2块{blk_1,blk_2},第一块放在h0、h1、h3,第二块放在h0、h2、h4,机器IP) #每一块为了保证安全存副本
得到这个元数据信息,可以随意选择到哪读取信息。
校验核机制:每个文件都有一个相应的值,在上传这个文件时原数据中保存这个值了,下载后产生一个真正的值,对比,如果不一样,说明文件损坏(用原始的校验值和该文件的校验值相比较)
NameNode
是整个文件系统的管理节点。它维护着整个文件系统的文件目录树。维护着文件/目录的元信息,和对应的数据块列表(每个数据分了多少块,每块分别是怎么存储的)。还接受用户的请求【客户端请求:上传下载删除文件】。还要操作一些datenode,进行一些块的复制。
文件包括:
fsimage——元数据的镜像文件。(为防止数据丢失,文件内存一份、磁盘一份)存放在磁盘上【不是内存上】的叫fsimage。存储某一时段NamwNode内存元数据信息,但(伪分布式)并不是实时同步,(集群模式)真正的分布式是实时同步
与之相对的,metadata存放在内存当中
edits:记录用户的操作日志。(该用户上传了一个文件,删除了一个文件,等等)
fstime:保存了用户最近一次checkpoint时间。即“保存最近一次做还原点的时间”
以上这些文件都是存在Linux文件系统里的,而不是HDFS。因为文件很小,在挂起的时候,将内存里的东西序列化到磁盘了,无需存在HDFS上
![]()
里面都是edits和fsimage文件。
NameNode的工作特点
namenode始终在内存中保存metadata【为了速度快】,用于处理用户的“读”请求。放在内存里当然很快了,放在磁盘里读的速度慢。
在“写”请求时,namenode首先向edits里面写日志,让edits里面记录一条,成功后再修改内存,让内存里面也加入一条信息,最后向客户端返回。
Hadoop会维护一个fsimage文件,也就是namenode中metedata的镜像,但是fsimage不会随时与namenode内存中的metedata保持一致,而是每隔一段时间通过合并edits文件来更新内容。Secondarynamenode就是用来合并fsimage和edits文件来更新NameNode的metedata的。【Secondarynamenode只有一个功能就是帮助Namenode合并文件】产生一个新的fsimage,用新的来替换旧的fsimage.
SecondaryNameNode:【集群里并没有,但伪分布式里面有】 下载——合并——推送
lHA的一个解决方案。但不支持热备。配置即可。l执行过程:从NameNode上下载元数据信息(fsimage,edits),然后把二者合并,生成新的fsimage,在本地保存,并将其推送到NameNode,替换旧的fsimage.l默认在安装在NameNode节点上,但这样...不安全!【hadoop2.0集群根本没有secondarynamenode,但伪分布式有】
secondary namenode的工作流程
1、secondary通知namenode切换edits文件
2、secondary从namenode获得fsimage和edits(通过http)
3、secondary将fsimage载入内存,然后开始合并edits
4、secondary将新的fsimage发回给namenode
5、namenode用新的fsimage替换旧的fsimage
内存到磁盘——序列化 磁盘到内存——反序列化
因为容易不安全,所以分在两个地方装namenode和secondarynamenode,如果一个烧掉了,另一个还在从namenode里下载edits和fsimage之后不能删除删除namenode里的这两个文件,防止中间出错,直到新的fsimage替换旧的fsimage成功,才可以删除。同时,若下载edits和fsimage过程中上传东西、合并文件、secondarynamenode正在数据同步时,则不能在原edits中写日志,要生成新的edits.new,以后上传东西的日志都写入新的中,等到新的fsimagge替换旧的fsimage后,把旧的edits文件删掉,接着将新的edits.new重命名回edits。【反复的保证数据的一致】上面那个黄色浅蓝的图,面试的时候很愿意考。关注一下(虽然现在2.0已经没有这种方式了,但很多公司老的技术经理对1比较熟悉)
什么时候checkpoint默认每1个小时,secondarynamenode,就要把两个合并一下。或者edits文件大于64M,就要合并【因为edits文件存储数据越来越大】如果我正在同步的时候,正在上传数据,那我要往edits.new里面写,![]()
1.client发送给namenode,2反馈给client,3开始在datanode里写数据,在3的同时,namenode要操作edits文件,(成功失败都记录),倘若写入成功,edit+1,且,内存中的Metadata也+1,fsimage中的数据不+1,当满足一定条件secondarynamenode工作进行合并。
此时edits和fsimage里的数据没有同步,用上面那个图的secondary图合并同步,同步需要满足checkpoint。前文已提到。
eg:两个月之前上传两个文件,matadata中有两条信息和上面时候上传无关,fsimage中有两条信息(fsimage已经合并多少次了,数据已经同步了),edits中0条(数据一合并,fsimage和edits合并,合并完之后edits要进行清空)