Hadoop HDFS源码namenode部分概述(二)

2019-03-28 13:53|来源: 网络

接着讲另外几个数据结构。

1.CorruptReplicationMap

成员变量:Map<Block, Collection<DatanodeDescriptor>> corruptReplicasMap用来记录datanode上出错的block,getNodes方法返回一个block在哪些datanode上的副本是corrupt的。在FSNamesystem中使用corruptReplicas保存这个map结构。

坏掉的block将放入recentInvalidateSets(Map<String, Collection<Block>>)中,Client或者datanode 通过reportBadBlocks报告出错的block,namenode调用FSNamesystem的markBlockAsCorrupt方法处理。

2.recentInvalidateSets

成员变量:Map<String, Collection<Block>> recentInvalidateSets

保存了每个Datanode上无效但还存在的block(StorageID-> ArrayList<Block>)

replthread后台任务线程中的computeInvalidateWork方法(实际方法是invalidateWorkForOneNode)取出map里第一个datanode节点上所有无效的block,然后将这个block列表设置到invalidateSet集合中,namenode收到心跳信息会依据自己保存的invalidateSet集合来生成一个invalidate blocks的命令返回给datanode,让datanode来处理这些无效的block。

3.UnderReplicatedBlocks

主要的成员是一个优先队列,List<TreeSet<Block>> priorityQueues,保存副本数没有达到期望值的block。根据当前副本数低于期望值的程度决定优先级,差的越远,优先级越大(0~2,0最大)。每个优先级别对应一个TreeSet,getPriority获得优先级后决定放入哪个treeset中。

在FSNamesystem中使用neededReplications保存低于规定副本数的block信息。

涉及neededReplications的一些操作:

当datanode注册到namenode时需要校验这个datanode是否处于正准备退役阶段,是则需要检测该datanode节点上的所有block的复制数是否已经达到复制因子,如果没有则需要加入到neededReplications中 ;

当DecommissionManager的监控线程dnthread执行检测时,如果发现某个退役节点处于正准备退役阶段,则对该退役节点的所有块执行检测,查看是否达到复制因子,如果没有达到则将该block加入到neededReplications中;

当lease被删除时,需要检测和这个租约关联的文件的block数是否和期望值一致,如果小于期望值则将这个块加入到neededReplications中;

当离开安全模式时需要校验block的副本情况,如果没达到副本因子数则加入到neededReplications中;

processPendingReplications方法将pendingReplicationMonitor中监控到的超时的副本拷贝请求重新放入neededReplications中去。

4.PendingReplicationBlocks

主要的成员是Map<Block, PendingBlockInfo> pendingReplications用来保存正在复制的数据块的相关信息。该类中还有一个timerThread,检测副本是否超时的线程;副本拷贝超时(5min)未成功的block 放入到ArrayList<Block> timedOutItems中。

超时的block在FSNamesystem的processPendingReplications方法中又将 timedOutItems 清空, 添加到neededReplications中。

5.excessReplicateMap

Map<String, Collection<Block>> excessReplicateMap

保存Datanode上有效但需要删除的数据块(StorageID -> TreeSet<Block>)比如一个Datanode故障恢复后,上面的数据块在系统中副本数太多,需要删除一些数据块。

6. LeaseManager

hdfs支持write-once-read-many,也就是说不支持并行写,那么对读写的互斥同步就是靠Lease实现的。Lease说白了就是一个有时间约束的锁。客户端写文件时需要先申请一个Lease,对应到namenode中的LeaseManager,客户端的client name就作为一个lease的holder,即租约持有者。LeaseManager维护了文件的path与lease的对应关系,还有clientname->lease的对应关系。LeaseManager中有两个时间限制:softLimit and hardLimit。

软限制就是写文件时规定的租约超时时间,硬限制则是考虑到文件close时未来得及释放lease的情况强制回收租约。

LeaseManager中还有一个Monitor线程来检测Lease是否超过hardLimit。而软租约的超时检测则在DFSClient的LeaseChecker中进行。

当客户端(DFSClient)create一个文件的时候,会通过RPC 调用 namenode 的createFile方法来创建文件。进而又调用FSNameSystem的startFile方法,又调用 LeaseManager 的addLease方法为新创建的文件添加一个lease。如果lease已存在,则更新该lease的lastUpdate (最近更新时间)值,并将该文件的path对应该lease上。之后DFSClient 将该文件的path 添加 LeaseChecker中。文件创建成功后,守护线程LeaseChecker会每隔一定时间间隔renew该DFSClient所拥有的lease。

另外还有一个数据结构:datanodemap,它保存了StorageID -> DatanodeDescriptor的映射,用于保证DataNode使用的Storage的一致性。

至此,namenode上的关键数据结构已经基本上讲完了。

接下来就是namenode上的一些监控线程。

<!--[if !supportLists]-->1.       <!--[endif]-->HeartbeatMonitor thread

datanode周期性通过RPC调用sendHeartbeat向namenode汇报自身的状态,心跳监控线程对dn和nn之间的心跳进行周期性检测,每隔时间heartbeatRecheckInterval 就执行操作heartbeatCheck()。

heartbeatCheck找到heartbeats中的dead nodes,然后从heartbeats 、clusterMap 、blocksmap这些结构中移除这些dead nodes的信息。

相关阅读:Hadoop HDFS源码namenode部分概述(一)  http://www.linuxidc.com/Linux/2012-03/57038.htm

更多Hadoop相关信息见Hadoop 专题页面 http://www.linuxidc.com/topicnews.aspx?tid=13

相关问答

更多
  • hadoop hdfs的问题[2021-10-30]

    最下面那张图里环境变量设置的那一行多了一个$符号 export JAVA_HOME=/usr/java/jdk1.6.0_35
  • 很酷,我找到了解决方案。 停止所有运行的服务器 1) stop-all.sh 编辑文件/usr/local/hadoop/conf/hdfs-site.xml并添加下面的配置(如果缺失) dfs.data.dir /app/hadoop/tmp/dfs/name/data true d ...
  • 在使用Hadoop的过程中,很容易通过FileSystem类的API来读取HDFS中的文件内容,读取内容的过程是怎样的呢?今天来分析客户端读取HDFS文件的过程,下面的一个小程序完成的功能是读取HDFS中某个目录下的文件内容,然后输出到控制台,代码如下: [java] view plain copy public class LoadDataFromHDFS { public static void main(String[] args) throws IOException { new LoadDataF ...
  • 这不是一个错误。 在启动HDFS之前,您需要格式化namenode。 这与运行Linux / Windows之前需要格式化磁盘相似。 This is not an error. Before you can start HDFS, you need to format the namenode. This is similar to before you can run Linux/Windows you need to format the disk.
  • 您的namenode取决于它正在做什么,可以处于几种状态之一。 例如,当它启动时,它处于安全模式 。 当您的namenode处于安全模式时 ,它将使用dfs.namenode.replication.min来覆盖dfs.namenode.replication设置。 一旦datanode报告了所有块, namenode将离开所述状态并返回使用原始设置。 Your namenode, depending on what it's doing, can be in one of several states. ...
  • 当我删除[hadoop临时目录] / dfs / namesecondary目录时,我遇到了同样的错误。 对我来说[hadoop临时目录]是core-site.xml中hadoop.tmp.dir的值 I had the same error and it went when I deleted the [hadoop temporary directory] /dfs/namesecondary directory. For me [hadoop temporary directory] is the v ...
  • 假设zipIn是java.util.zip.ZipInputStream ,你不应该迭代地调用getNextEntry而不是读取字节吗? I resolved this issue after doing some changes in my code. In the first part of code, I was trying to unzip all the zip files whereas I should have access the spilts. Hadoop basic, which ...
  • 下载osquery https://code.facebook.com/projects/658950180885092 并安装 发出这个命令osqueryi 当出现提示时,使用此sql命令查看所有正在运行的java进程并找到pids SELECT名称,路径,pid FROM进程,其中name =“java”; 你会在Mac上看到这样的东西 +------+-------------------------------------------------------------------------- ...
  • HDFS高可用性和HDFS联合之间的主要区别在于联合中的名称节点彼此不相关。 在HDFS联合中,所有名称节点共享一个元数据池,其中每个名称节点都有自己的池,因此提供了容错功能,即如果联合中的一个名称节点失败,则不会影响其他名称节点的数据。 所以,Federation =多个名称节点,没有相关性。 在HDFS HA的情况下,有两个名称节点 - 主NN和备用NN。 主NN每次都很努力,而Standby NN只是坐在那里,并且偶尔会对主要Namenode的元数据进行冷却和更新,这使得它们相关。 当主要NN厌倦了这 ...
  • 我假设您已屏蔽并共享您的网址 hdfs://vikasXXX.XX.XX.XX:X000 我认为它无法通过名称识别您的机器。 尝试使用localhost并检查它是否有效。 hdfs://localhost:8020 I assume that you have masked and shared your URL hdfs://vikasXXX.XX.XX.XX:X000 I think it is not recognizing your machine by name. Try using localh ...