Hadoop中提供了balancer的机制,解决小弟我的hive统计group有关问题

Hadoop中提供了balancer的机制,解决我的hive统计group问题
如果是select * from saleslog where `date`='2012-02-29' limit 5;这句是可以吐出五条数据的。
但是如下却出错了。。
hive> select goods_name,count(1) from saleslog where `date`='2012-02-29' group by goods_name;
Total MapReduce jobs = 1
Launching Job 1 out of 1
Number of reduce tasks not specified. Defaulting to jobconf value of: 5
In order to change the average load for a reducer (in bytes):
  set hive.exec.reducers.bytes.per.reducer=<number>
In order to limit the maximum number of reducers:
  set hive.exec.reducers.max=<number>
In order to set a constant number of reducers:
  set mapred.reduce.tasks=<number>
Starting Job = job_201203160945_0233, Tracking URL = http://mh-s002a.hadoop:50030/jobdetails.jsp?jobid=job_201203160945_0233
Kill Command = /opt/hadoop/bin/hadoop job -Dmapred.job.tracker=mh-s002a.hadoop:9001 -kill job_201203160945_0233
2012-03-26 14:41:36,470 Stage-1 map = 0%, reduce = 0%
2012-03-26 14:41:40,494 Stage-1 map = 100%, reduce = 100%
Ended Job = job_201203160945_0233 with errors
FAILED: Execution Error, return code 2 from org.apache.hadoop.hive.ql.exec.MapRedTask

因为数据节点的磁盘大小相差比较大..有的只有50G .有的有200多G  集群运行了一段时间.. 50G的被塞满了. 在跑 HIVE任务的时候.需要临时空间.. 分配不到 所以上午那个就报错了..  
后来我运行 /opt/hadoop/bin/hadoop balancer -threshold 20   进行一个 磁盘空间的平衡..现在 跑HIVE应该就不会报错了



对于HDFS集群,经常长时间的运行,尤其是大量的delete操作后,集群中各个Datanode上的空间使用率可能会存在比较大的差异。
所以需要一种机制使各个Datanode保持平衡,防止少数Datanode存储过多的文件。
少数使用率过高的Datanode会导致对其的数据访问效率变低,并且如果该Datanode挂掉,需要更多的时间进行恢复,对集群也会造成更大的影响。
Hadoop 中已经提供了balancer 的机制。

hadoop balancer -threshold <threshold>

通过上面的命令可以是Hadoop 对各个Datanode进行评估并使他们保持平衡。
参数threshold表示的平衡的阀值,取值范围在0%到100%之间。
该参数表示每个Datanode中空间使用率与HDFS集群总的空间使用率的差距百分比。

假如当前集群总空间为20T,已经空间为10T,那么对于HDFS集群来说空间使用率为50%。
当前集群有2台Datanode,每台有10T总空间。
Datanode 1已用空间为4T,那么Datanode的空间使用率为40%
Datanode 2已用空间为6T,那么Datanode的空间使用率为60%
如果我设置balancer 的阀值为10%,那么此时两台Datanode的使用率与HDFS的总使用率的比值均超过阀值,此时需要执行balancer
如果我设置balancer 的阀值为50%,那么此时两台Datanode的使用率与HDFS的总使用率的比值均未超过阀值,此时不需要执行balancer

阀值设置的越小,那么HDFS各个Datanode的使用率越接近,整个集群也更加的平衡,但会需要消耗更多的时间和资源来达到该平衡状态。
如果阀值设置的过小,那么对于操作非常频繁的HDFS集群,有可能永远也不会达到该阀值所指定的平衡状态。
阀值设置的越大,那么HDFS各个Datanode的使用率差距越大,但是会较容易达到。

balancer 的过程,hadoop 会递归的把BLOCK从使用率高的Datanode转移到那些使用率低的Datanode上。
在每次递归的过程中,单个Datanode转移或者接受的BLOCK不过超过10G或者它存储能力的阀值(根据该Datanode的总空间决定)。
并且每次递归过程也不能执行超过20分钟。
在每次递归过后,会更新Datanode的最新状态信息,决定下一次递归的执行。

通过参数dfs.balance.bandwidthPerSec可以现在balancer 过程所占用的网络带宽,单位为每秒字节数,默认值为1M。
如果你的集群比较空闲或者带宽比较大,可以适当的增加该参数,来加速整个balancer 过程。
如果你的集群比较繁忙或者带宽比较小,就要调小该参数,但这个balancer 过程会变得缓慢。
对该参数的参数,只有在HDFS下次启动后才可以生效。

整个balancer 过程还是比较复杂的,首先会计算集群总的使用率,然后分别计算各个活着的Datanode结点的使用率。
根据balancer 阀值对各个Datanode进行分类,找到那些使用率过高的和使用率过低的结点。
遍历使用率过高的结点,找到适合迁移BLOCK的目标结点,原则就是最好是同一机架,如果当前机架没有适合的才会考虑其他机架。
把BLOCK从使用率高的结点拷贝到使用率低的结点,完成一次递归过程后重新计算使用率,判断使用需要进行下一次过程。
整个递归过程,最多会执行5次。

 

 

 

Hadoop的HDFS集群非常容易出现机器与机器之间磁盘利用率不平衡的情况,比如集群中添加新的数据节点。当HDFS出现不平衡状况的时候,将 引发很多问题,比如MR程序无法很好地利用本地计算的优势,机器之间无法达到更好的网络带宽使用率,机器磁盘无法利用等等。可见,保证HDFS中的数据平 衡是非常重要的。

在Hadoop中,包含一个Balancer程序,通过运行这个程序,可以使得HDFS集群达到一个平衡的状态,使用这个程序的命令如下:

sh $HADOOP_HOME/bin/start-balancer.sh –t 10%

这个命令中-t参数后面跟的是HDFS达到平衡状态的磁盘使用率偏差值。如果机器与机器之间磁盘使用率偏差小于10%,那么我们就认为HDFS集群已经达到了平衡的状态。

Hadoop的开发人员在开发Balancer程序的时候,遵循了以下几点原则:

1.    在执行数据重分布的过程中,必须保证数据不能出现丢失,不能改变数据的备份数,不能改变每一个rack中所具备的block数量。

2.    系统管理员可以通过一条命令启动数据重分布程序或者停止数据重分布程序。

3.    Block在移动的过程中,不能暂用过多的资源,如网络带宽。

4.    数据重分布程序在执行的过程中,不能影响name node的正常工作。

基于这些基本点,目前Hadoop数据重分布程序实现的逻辑流程如下图所示:

 

 

Hadoop中提供了balancer的机制,解决小弟我的hive统计group有关问题

Rebalance程序作为一个独立的进程与name node进行分开执行。

1 Rebalance Server从Name Node中获取所有的Data Node情况:每一个Data Node磁盘使用情况。

2 Rebalance Server计算哪些机器需要将数据移动,哪些机器可以接受移动的数据。并且从Name Node中获取需要移动的数据分布情况。

3 Rebalance Server计算出来可以将哪一台机器的block移动到另一台机器中去。

4,5,6 需要移动block的机器将数据移动的目的机器上去,同时删除自己机器上的block数据。

7  Rebalance Server获取到本次数据移动的执行结果,并继续执行这个过程,一直没有数据可以移动或者HDFS集群以及达到了平衡的标准为止。

Hadoop现有的这种Balancer程序工作的方式在绝大多数情况中都是非常适合的。

现在我们设想这样一种情况:

1 数据是3份备份。

2 HDFS由2个rack组成。

3 2个rack中的机器磁盘配置不同,第一个rack中每一台机器的磁盘空间为1TB,第二个rack中每一台机器的磁盘空间为10TB。

4 现在大多数数据的2份备份都存储在第一个rack中。

在这样的一种情况下,HDFS级群中的数据肯定是不平衡的。现在我们运行Balancer程序,但是会发现运行结束以后,整个HDFS集群中的数据依旧不平衡:rack1中的磁盘剩余空间远远小于rack2。

这是因为Balance程序的开发原则1导致的。

简单的说,就是在执行Balancer程序的时候,不会将数据中一个rack移动到另一个rack中,所以就导致了Balancer程序永远无法平衡HDFS集群的情况。

针对于这种情况,可以采取2中方案:

1 继续使用现有的Balancer程序,但是修改rack中的机器分布。将磁盘空间小的机器分叉到不同的rack中去。

2 修改Balancer程序,允许改变每一个rack中所具备的block数量,将磁盘空间告急的rack中存放的block数量减少,或者将其移动到其他磁盘空间富余的rack中去。

更多关于Hadoop的文章,可以参考:http://www.cnblogs.com/gpcuster/tag/Hadoop/