文档名称:Hadoop 基线选定




                   Hadoop 基线选定



文档版本控制
 文档版本号    日期        作者    审核人   说明
 V0.1               刘景龙
文档名称:Hadoop 基线选定




1. 需求
    由“HBase 使用 hadoop 分析.doc ”结果,HBase 对 Hadoop 需求主要分为以下 2 方面:
    稳定性:
    (1) HDFS 处理不致命的错误。
    (2) Datanode 坏盘应对 hbase 透明
    (3) Region server 到 datanode 连接数可控
    (4) Sync() 功能支持(sequence file flush 语义的支持)。

    性能:
    (5) 提高 HDFS 随机读性能
    (6) Client 端到 datanode 连接重用


2. 版本选择

2.1 备选版本
  当前 hadoop 版本中对 append/sync 功能支持的包括 CDH3b2,0.20-append,0.21.0
,所以我们选择此 3 个版本作为备选版本。



2.2 备选版本对需求的满足
各版本对 hbase 需求的满足状况:


                需求 1       需求 2         需求 3       需求 4          需求 5        需求 6
CDH3b2          ×          ○            ×          ○             ×           ×
0.21.0          ×          ×            ×          ○             ×           ×
0.20.2-append   ×          ×            ×          ○             ×           ×
注: ×为不支持, ○为支持

各版本优缺点:
                       Append/sync 支持   是否 release           兼容             是否针对
                                                             hadoop0.20.2   hbase 进行
                                                                            优化
CDH3b2              基于 HADOOP-1700      否                    是              是
                    实现                  (facebook,cloudera
                                        推荐)
0.21.0              基于 HDFS-265 实现      是 (无大规模使             未知             否
                                        用, 且.0 为非稳
                                        定 release)
0.20.2-append       基于 HADOOP-1700      否                    是              是
文档名称:Hadoop 基线选定


                 实现                        (facebook,cloudera
                                           推荐)
注:
  HADOOP-1700 为 2008-07-24 提交,经过 2 年 bug fix。
  HDFS-265 为 2010-05-21 提交设计文档,并合并入 0.21.0。

     由于 0.21.0 该版本为非稳定 release,并未经过测试使用,引入了大量不兼容改变,且
其并不能比其他版本更好的满足 hbase 的需求,所以我们暂不选择 hadoop 0.21.0。
    我们选择 cdh3b2 进行功能测试,主要测试 append/sync 功能的实现状况。具体测试用例
请见附录。由测试用例得出结论,基于 HADOOP-1700 的 append/sync 实现可以满足需求。
    下面我们对比 cdh3b2 和 0.20-append, 对比这两个版本。
    在社区支持方面,0.20-append 主要由 facebook 在推动,而 CDH3b2 则是有 cloudera 在
推动,比较社区支持而言,不相伯仲。
    我们比较下 cdh3b2 和 0.20-append 在功能上的差别。这两个版本在主要功能和采用的
patch 上大同小异。下表中对比了两个版本特有的 patch。
     Cdh3                                                   0.20-append
稳定   [HDFS-1056] - Multi-node RPC deadlocks during          HDFS-1258 Clearing namespace quota on
性    block recovery                                         "/" corrupts fs image.
     [HDFS-1122] - client block verification may result     HDFS-955 New implementation of
     in blocks in DataBlockScanner prematurely              saveNamespace() to avoid loss of edits
     [HDFS-1197] - Blocks are considered "complete"
     prematurely after commitBlockSynchronization or
     DN restart
     [HDFS-1186] - 0.20: DNs should interrupt writers at
     start of recovery
     [HDFS-1218] - 20 append: Blocks recovered on
     startup should be treated with lower priority during
     block synchronization
     [HDFS-1260] - 0.20: Block lost when multiple DNs
     trying to recover it to different genstamps
     [HDFS-127] - DFSClient block read failures cause
     open DFSInputStream to become unusable
     [HDFS-686] - NullPointerException is thrown while
     merging edit log and image
     [HDFS-915] - Hung DN stalls write pipeline for far
     longer than its timeout
     [HADOOP-6269] - Missing synchronization for
     defaultResources in Configuration.addResource
     [HADOOP-6460] - Namenode runs of out of
     memory due to memory leak in ipc Server
     [HADOOP-6667] - RPC.waitForProxy should retry
     through NoRouteToHostException
     [HADOOP-6722] - NetUtils.connect should check
     that it hasn't connected a socket to itself
文档名称:Hadoop 基线选定


       [HADOOP-6723] - unchecked exceptions thrown in
       IPC Connection orphan clients
       [HADOOP-6724] - IPC doesn't properly handle
       IOEs thrown by socket factory
       [HADOOP-6762] - exception while doing RPC I/O
       closes channel
       [HADOOP-2366] - Space in the value for
       dfs.data.dir can cause great problems
       [HADOOP-4885] - Try to restore failed replicas of
       Name Node storage (at checkpoint time)


功能     [HDFS-142] - In 0.20, move blocks being written
       into a blocksBeingWritten directory
       [HDFS-611] - Heartbeats times from Datanodes
       increase when there are plenty of blocks to delete
       [HDFS-895] - Allow hflush/sync to occur in parallel
       with new writes to the file
       [HDFS-877] - Client-driven block verification not
       functioning
       [HDFS-894] - DatanodeID.ipcPort is not updated
       when existing node re-registers


性能     [HADOOP-4655] - FileSystem.CACHE should be              HDFS-1041
       ref-counted                                             DFSClient.getFileChecksum(..)      should
                                                               retry if connection to
                                                               HDFS-927 DFSInputStream retries too
                                                               many times for new block locations
Misc   [HDFS-1161] - Make DN minimum valid volumes             HADOOP-6637           Benchmark         for
       configurable                                            establishing RPC session. (shv)
       [HDFS-1209]             -           Add          conf   HADOOP-6760         WebServer shouldn't
       dfs.client.block.recovery.retries to configure number   increase port number in case of negative
       of block recovery attempts
       [HDFS-455] - Make NN and DN handle in a
       intuitive way comma-separated configuration strings
       [HDFS-528] - Add ability for safemode to wait for a
       minimum number of live datanodes
       [HADOOP-1849] - IPC server max queue size
       should be configurable
       [HADOOP-4675] - Current Ganglia metrics
       implementation is incompatible with Ganglia 3.1
       [HADOOP-4829] - Allow FileSystem shutdown
       hook to be disabled
       [HADOOP-5257] - Export namenode/datanode
       functionality through a pluggable RPC layer
文档名称:Hadoop 基线选定


     [HADOOP-5450]          -    Add       support for
     application-specific typecodes to typed bytes
     [HADOOP-5891] - If dfs.http.address is default,
     SecondaryNameNode can't find NameNode



       由上表我们不难发现,CDH3b2 和 0.20-append 增加了更多的稳定性改进和 append
   功能的 bug fix。而 0.20-append 中特有的一些 patch,也引入了很重要的改进。我们的目
   标是鱼与熊掌兼得。所以,我们选择以 cdh3b2 作为基线版本。并将 0.20-append 中引入
   的 patch,排期进行 merge。


3. 结论
       三个备选版本都能够支持 append/sync 功能,其中 CDH3b2 和 0.20.0 – append 两个
   版本是基于相对较稳定的 hadoop 0.20.2,而 hadoop 0.21.0 是一个新的大版本,    (且.0 版
   本为非稳定 release) ,未经过长期使用和测试,所以我们优先选择 CDH3b2 和 0.20.0 –
   append。
       在 CDH3b2 和 0.20.0 – append 这两个版本的比较中,CDH3b2 相对 0.20.0-append
   对于系统稳定性和 append 功能支持,拥有更多的改进,所以我们选择 CDH3b2 作为基
   线版本。而 0.20-append 中引入的 6 个 patch,我们会按照“稳定性-功能-性能”的优先
   级顺序,排期进行 merge。
       所以我们选择 CDH3b2 作为 for hbase 的基线版本。
文档名称:Hadoop 基线选定




附录
Append 测试
    以下 append 测试为官方提供的 append unit test。基于 Mini cluster 进行测试。为验证
append/sync 功能在实际集群工作状况,我们在真正集群进行了 append/sync 功能测试
(TestFileAppend 中),case 通过。
FileAppend:主要进行 sync 和 append 功能的简单测试
testComplexFlush()
     创建文件
     写入
     Sync
     检查文件内容
     写入
     Close
     检查文件内容
testSimpleFlush()
    创建文件
    写半个文件
    Sync
    再写后半个文件
    Sync
    检查文件内容
    Close
    检查文件内容
FileAppend2: 主要进行 sync 和 append 功能的简单测试
testComplexAppend()
     模拟多线程对多个文件 append 操作
testSimpleAppend()
     创建文件
     写入 (不满 io.bytes.per.checksum)
     Close
    写入(不满 2 个 io.bytes.per.checksum)
    Close
    写入文件剩下部分
    Close
    验证文件大小



FileAppend3 主要进行 sync 和 append 功能的符合场景测试。主要是验证跨块和
跨 checksum 的情景的正确性。

testTC1()
     创建文件
文档名称:Hadoop 基线选定


   写 1 个 block
   Close 文件
   以 Append 方式打开文件
   写 0.5 个 block
   Close
   读取 1.5 个 block 并验证文件内容

testTC2()
     创建文件
     写文件 1.5 block
     Close
     Append
     写 1/4 block
     Close
     读 1.75 个 block 并验证文件内容

testTC5()
     clientA 创建文件
     clientA 写入半个块
     clientA close 文件
     clientA append 文件
     client append 文件(期待报错)

testTC7()
     创建文件
     写入半个块
     close 文件
     使一个 datanode 的块 corrupt
     append 文件
     close 文件
     验证文件大小

testTC12()
     创建文件
     写入 25687B
     close 文件
     append 文件
     写入 5877B
     close 文件
     验证文件大小
     [注]: hdfs 是每 io.bytes.per.checksum(默认为 512),进行一次 checksum。此 case 用于
验证跨 checksum 的时候,append 是否可以生效。

FileAppend4 主要进行 sync 和 append 功能的 fail over 测试
文档名称:Hadoop 基线选定


testAppendSyncBbw()
     clientA 创建文件
     写入 500B
     Sync
     Client A 失去 lease
     Client B 进行 lease recovery
     Client B 验证文件内容
testAppendSyncBbwClusterRestart()
     clientA 创建文件
     写入 500B
     Sync
     集群重启
     Client B 进行 lease recovery
     Client B 验证文件内容
testAppendSyncChecksum0()
     创建文件
     写 1/2 block
     Sync
     停掉集群
     损坏第 1 个 datanode 对应 block 的 checksum
     重启集群
     验证文件内容
testAppendSyncChecksum1()
     创建文件
     写 1/2 block
     Sync
     停掉集群
     损坏第 2 个 datanode 对应 block 的 checksum
     重启集群
     验证文件内容
testAppendSyncChecksum2()
     创建文件
     写 1/2 block
     Sync
     停掉集群
     损坏第 3 个 datanode 对应 block 的 checksum
     重启集群
     验证文件内容
testAppendSyncReplication0()
     创建文件
     写 1/2 block
     Sync
     停掉第 1 个 datanode
     再写 1/4 个 block
文档名称:Hadoop 基线选定


     Sync
     重启集群
     验证文件内容
testAppendSyncReplication1()
     创建文件
     写 1/2 block
     Sync
     停掉第 2 个 datanode
     再写 1/4 个 block
     Sync
     重启集群
     验证文件内容
testAppendSyncReplication2()
     创建文件
     写 1/2 block
     Sync
     停掉第 3 个 datanode
     再写 1/4 个 block
     Sync
     重启集群
     验证文件内容
testDnDeath0()
     写完成后,停掉第一个 datanode,进行 lease recovery,然后验证文件内容。
testDnDeath1()
     写完成后,停掉第二个 datanode,进行 lease recovery,然后验证文件内容。
testDnDeath2()
     写完成后,停掉第三个 datanode,进行 lease recovery,然后验证文件内容。
testFullClusterPowerLoss()
     写入半个 block,sync,      然后模拟机房断电,然后重启后,   验证文件内容。假设 page cache
                                                         (
可以刷到磁盘)
testHalfLengthPrimaryDN()
     模拟 DFSClient 正在写的过程中,其所在机器断电(datanode 块写到一半)的情景
testRecoverFinalizedBlock()
     验证 block 被 finalize,但是文件还没有被 complete 的 case (lease recovery 应该受到
Could not complete file 异常)
testTruncatedPrimaryDN()
     模拟 DFSClient 正在写的过程中,其所在机器断电(datanode 块文件还没有被写入)的
情景

Hadoop基线选定

  • 1.
    文档名称:Hadoop 基线选定 Hadoop 基线选定 文档版本控制 文档版本号 日期 作者 审核人 说明 V0.1 刘景龙
  • 2.
    文档名称:Hadoop 基线选定 1. 需求 由“HBase 使用 hadoop 分析.doc ”结果,HBase 对 Hadoop 需求主要分为以下 2 方面: 稳定性: (1) HDFS 处理不致命的错误。 (2) Datanode 坏盘应对 hbase 透明 (3) Region server 到 datanode 连接数可控 (4) Sync() 功能支持(sequence file flush 语义的支持)。 性能: (5) 提高 HDFS 随机读性能 (6) Client 端到 datanode 连接重用 2. 版本选择 2.1 备选版本 当前 hadoop 版本中对 append/sync 功能支持的包括 CDH3b2,0.20-append,0.21.0 ,所以我们选择此 3 个版本作为备选版本。 2.2 备选版本对需求的满足 各版本对 hbase 需求的满足状况: 需求 1 需求 2 需求 3 需求 4 需求 5 需求 6 CDH3b2 × ○ × ○ × × 0.21.0 × × × ○ × × 0.20.2-append × × × ○ × × 注: ×为不支持, ○为支持 各版本优缺点: Append/sync 支持 是否 release 兼容 是否针对 hadoop0.20.2 hbase 进行 优化 CDH3b2 基于 HADOOP-1700 否 是 是 实现 (facebook,cloudera 推荐) 0.21.0 基于 HDFS-265 实现 是 (无大规模使 未知 否 用, 且.0 为非稳 定 release) 0.20.2-append 基于 HADOOP-1700 否 是 是
  • 3.
    文档名称:Hadoop 基线选定 实现 (facebook,cloudera 推荐) 注: HADOOP-1700 为 2008-07-24 提交,经过 2 年 bug fix。 HDFS-265 为 2010-05-21 提交设计文档,并合并入 0.21.0。 由于 0.21.0 该版本为非稳定 release,并未经过测试使用,引入了大量不兼容改变,且 其并不能比其他版本更好的满足 hbase 的需求,所以我们暂不选择 hadoop 0.21.0。 我们选择 cdh3b2 进行功能测试,主要测试 append/sync 功能的实现状况。具体测试用例 请见附录。由测试用例得出结论,基于 HADOOP-1700 的 append/sync 实现可以满足需求。 下面我们对比 cdh3b2 和 0.20-append, 对比这两个版本。 在社区支持方面,0.20-append 主要由 facebook 在推动,而 CDH3b2 则是有 cloudera 在 推动,比较社区支持而言,不相伯仲。 我们比较下 cdh3b2 和 0.20-append 在功能上的差别。这两个版本在主要功能和采用的 patch 上大同小异。下表中对比了两个版本特有的 patch。 Cdh3 0.20-append 稳定 [HDFS-1056] - Multi-node RPC deadlocks during HDFS-1258 Clearing namespace quota on 性 block recovery "/" corrupts fs image. [HDFS-1122] - client block verification may result HDFS-955 New implementation of in blocks in DataBlockScanner prematurely saveNamespace() to avoid loss of edits [HDFS-1197] - Blocks are considered "complete" prematurely after commitBlockSynchronization or DN restart [HDFS-1186] - 0.20: DNs should interrupt writers at start of recovery [HDFS-1218] - 20 append: Blocks recovered on startup should be treated with lower priority during block synchronization [HDFS-1260] - 0.20: Block lost when multiple DNs trying to recover it to different genstamps [HDFS-127] - DFSClient block read failures cause open DFSInputStream to become unusable [HDFS-686] - NullPointerException is thrown while merging edit log and image [HDFS-915] - Hung DN stalls write pipeline for far longer than its timeout [HADOOP-6269] - Missing synchronization for defaultResources in Configuration.addResource [HADOOP-6460] - Namenode runs of out of memory due to memory leak in ipc Server [HADOOP-6667] - RPC.waitForProxy should retry through NoRouteToHostException [HADOOP-6722] - NetUtils.connect should check that it hasn't connected a socket to itself
  • 4.
    文档名称:Hadoop 基线选定 [HADOOP-6723] - unchecked exceptions thrown in IPC Connection orphan clients [HADOOP-6724] - IPC doesn't properly handle IOEs thrown by socket factory [HADOOP-6762] - exception while doing RPC I/O closes channel [HADOOP-2366] - Space in the value for dfs.data.dir can cause great problems [HADOOP-4885] - Try to restore failed replicas of Name Node storage (at checkpoint time) 功能 [HDFS-142] - In 0.20, move blocks being written into a blocksBeingWritten directory [HDFS-611] - Heartbeats times from Datanodes increase when there are plenty of blocks to delete [HDFS-895] - Allow hflush/sync to occur in parallel with new writes to the file [HDFS-877] - Client-driven block verification not functioning [HDFS-894] - DatanodeID.ipcPort is not updated when existing node re-registers 性能 [HADOOP-4655] - FileSystem.CACHE should be HDFS-1041 ref-counted DFSClient.getFileChecksum(..) should retry if connection to HDFS-927 DFSInputStream retries too many times for new block locations Misc [HDFS-1161] - Make DN minimum valid volumes HADOOP-6637 Benchmark for configurable establishing RPC session. (shv) [HDFS-1209] - Add conf HADOOP-6760 WebServer shouldn't dfs.client.block.recovery.retries to configure number increase port number in case of negative of block recovery attempts [HDFS-455] - Make NN and DN handle in a intuitive way comma-separated configuration strings [HDFS-528] - Add ability for safemode to wait for a minimum number of live datanodes [HADOOP-1849] - IPC server max queue size should be configurable [HADOOP-4675] - Current Ganglia metrics implementation is incompatible with Ganglia 3.1 [HADOOP-4829] - Allow FileSystem shutdown hook to be disabled [HADOOP-5257] - Export namenode/datanode functionality through a pluggable RPC layer
  • 5.
    文档名称:Hadoop 基线选定 [HADOOP-5450] - Add support for application-specific typecodes to typed bytes [HADOOP-5891] - If dfs.http.address is default, SecondaryNameNode can't find NameNode 由上表我们不难发现,CDH3b2 和 0.20-append 增加了更多的稳定性改进和 append 功能的 bug fix。而 0.20-append 中特有的一些 patch,也引入了很重要的改进。我们的目 标是鱼与熊掌兼得。所以,我们选择以 cdh3b2 作为基线版本。并将 0.20-append 中引入 的 patch,排期进行 merge。 3. 结论 三个备选版本都能够支持 append/sync 功能,其中 CDH3b2 和 0.20.0 – append 两个 版本是基于相对较稳定的 hadoop 0.20.2,而 hadoop 0.21.0 是一个新的大版本, (且.0 版 本为非稳定 release) ,未经过长期使用和测试,所以我们优先选择 CDH3b2 和 0.20.0 – append。 在 CDH3b2 和 0.20.0 – append 这两个版本的比较中,CDH3b2 相对 0.20.0-append 对于系统稳定性和 append 功能支持,拥有更多的改进,所以我们选择 CDH3b2 作为基 线版本。而 0.20-append 中引入的 6 个 patch,我们会按照“稳定性-功能-性能”的优先 级顺序,排期进行 merge。 所以我们选择 CDH3b2 作为 for hbase 的基线版本。
  • 6.
    文档名称:Hadoop 基线选定 附录 Append 测试 以下 append 测试为官方提供的 append unit test。基于 Mini cluster 进行测试。为验证 append/sync 功能在实际集群工作状况,我们在真正集群进行了 append/sync 功能测试 (TestFileAppend 中),case 通过。 FileAppend:主要进行 sync 和 append 功能的简单测试 testComplexFlush() 创建文件 写入 Sync 检查文件内容 写入 Close 检查文件内容 testSimpleFlush() 创建文件 写半个文件 Sync 再写后半个文件 Sync 检查文件内容 Close 检查文件内容 FileAppend2: 主要进行 sync 和 append 功能的简单测试 testComplexAppend() 模拟多线程对多个文件 append 操作 testSimpleAppend() 创建文件 写入 (不满 io.bytes.per.checksum) Close 写入(不满 2 个 io.bytes.per.checksum) Close 写入文件剩下部分 Close 验证文件大小 FileAppend3 主要进行 sync 和 append 功能的符合场景测试。主要是验证跨块和 跨 checksum 的情景的正确性。 testTC1() 创建文件
  • 7.
    文档名称:Hadoop 基线选定 写 1 个 block Close 文件 以 Append 方式打开文件 写 0.5 个 block Close 读取 1.5 个 block 并验证文件内容 testTC2() 创建文件 写文件 1.5 block Close Append 写 1/4 block Close 读 1.75 个 block 并验证文件内容 testTC5() clientA 创建文件 clientA 写入半个块 clientA close 文件 clientA append 文件 client append 文件(期待报错) testTC7() 创建文件 写入半个块 close 文件 使一个 datanode 的块 corrupt append 文件 close 文件 验证文件大小 testTC12() 创建文件 写入 25687B close 文件 append 文件 写入 5877B close 文件 验证文件大小 [注]: hdfs 是每 io.bytes.per.checksum(默认为 512),进行一次 checksum。此 case 用于 验证跨 checksum 的时候,append 是否可以生效。 FileAppend4 主要进行 sync 和 append 功能的 fail over 测试
  • 8.
    文档名称:Hadoop 基线选定 testAppendSyncBbw() clientA 创建文件 写入 500B Sync Client A 失去 lease Client B 进行 lease recovery Client B 验证文件内容 testAppendSyncBbwClusterRestart() clientA 创建文件 写入 500B Sync 集群重启 Client B 进行 lease recovery Client B 验证文件内容 testAppendSyncChecksum0() 创建文件 写 1/2 block Sync 停掉集群 损坏第 1 个 datanode 对应 block 的 checksum 重启集群 验证文件内容 testAppendSyncChecksum1() 创建文件 写 1/2 block Sync 停掉集群 损坏第 2 个 datanode 对应 block 的 checksum 重启集群 验证文件内容 testAppendSyncChecksum2() 创建文件 写 1/2 block Sync 停掉集群 损坏第 3 个 datanode 对应 block 的 checksum 重启集群 验证文件内容 testAppendSyncReplication0() 创建文件 写 1/2 block Sync 停掉第 1 个 datanode 再写 1/4 个 block
  • 9.
    文档名称:Hadoop 基线选定 Sync 重启集群 验证文件内容 testAppendSyncReplication1() 创建文件 写 1/2 block Sync 停掉第 2 个 datanode 再写 1/4 个 block Sync 重启集群 验证文件内容 testAppendSyncReplication2() 创建文件 写 1/2 block Sync 停掉第 3 个 datanode 再写 1/4 个 block Sync 重启集群 验证文件内容 testDnDeath0() 写完成后,停掉第一个 datanode,进行 lease recovery,然后验证文件内容。 testDnDeath1() 写完成后,停掉第二个 datanode,进行 lease recovery,然后验证文件内容。 testDnDeath2() 写完成后,停掉第三个 datanode,进行 lease recovery,然后验证文件内容。 testFullClusterPowerLoss() 写入半个 block,sync, 然后模拟机房断电,然后重启后, 验证文件内容。假设 page cache ( 可以刷到磁盘) testHalfLengthPrimaryDN() 模拟 DFSClient 正在写的过程中,其所在机器断电(datanode 块写到一半)的情景 testRecoverFinalizedBlock() 验证 block 被 finalize,但是文件还没有被 complete 的 case (lease recovery 应该受到 Could not complete file 异常) testTruncatedPrimaryDN() 模拟 DFSClient 正在写的过程中,其所在机器断电(datanode 块文件还没有被写入)的 情景