Hadoop NameNode 高可用 (High Availability HA配置实现)

在 Hadoop 1.0 时代,Hadoop 的两大核心组件 HDFS NameNode 和 JobTracker 都存在着单点问题,这其中以 NameNode 的单点问题尤为严重。因为 NameNode 保存了整个 HDFS 的元数据信息,一旦 NameNode 挂掉,整个 HDFS 就无法访问,同时 Hadoop 生态系统中依赖于 HDFS 的各个组件,包括 MapReduce、Hive、Pig 以及 HBase 等也都无法正常工作,并且重新启动 NameNode 和进行数据恢复的过程也会比较耗时。这些问题在给 Hadoop 的使用者带来困扰的同时,也极大地限制了 Hadoop 的使用场景,使得 Hadoop 在很长的时间内仅能用作离线存储和离线计算,无法应用到对可用性和数据一致性要求很高的在线应用场景中。
所幸的是,在 Hadoop2.0 中,HDFS NameNode 和 YARN ResourceManger(JobTracker 在 2.0 中已经被整合到 YARN ResourceManger 之中) 的单点问题都得到了解决,经过多个版本的迭代和发展,目前已经能用于生产环境。HDFS NameNode 和 YARN ResourceManger 的高可用 (High Availability,HA) 方案基本类似,两者也复用了部分代码,但是由于 HDFS NameNode 对于数据存储和数据一致性的要求比 YARN ResourceManger 高得多,所以 HDFS NameNode 的高可用实现更为复杂一些,本文主要讲解HA的配置及实现

停止集群和备份配置

stop-dfs.sh,然后备份master机器上的core-site.xml hdfs-site.xml

在master上的hadoop的hdfs-site.xml增加如下的配置

<property>
   		 <name>dfs.nameservices</name>
          <value>mycluster</value>
		 <description>HDFS名字节点服务的逻辑名称,可以是任意值,但是需要和下面的名字保持一致</description>
  </property>
  <property>
          <name>dfs.ha.namenodes.mycluster</name>
          <value>nn1,nn2</value>
          <description>每一个NameNode在集群中的唯一标识</description>
  </property>
  <property>
          <name>dfs.namenode.rpc-address.mycluster.nn1</name>
          <value>master:8020</value>
 <description>nn1这个名字节点在RPC的时候使用的端口</description>
  </property>
  <property>
          <name>dfs.namenode.rpc-address.mycluster.nn2</name>
          <value>slave1:8020</value>
          <description>nn2这个名字节点在RPC的时候使用的端口</description>
  </property>
  <property>
         	 <name>dfs.namenode.http-address.mycluster.nn1</name>
            <value>master:50070</value>
   			 <description>nn1这个NameNode对外提供的http服务的端口</description>
    </property>
    <property>
            <name>dfs.namenode.http-address.mycluster.nn2</name>
            <value>slave1:50070</value>
            <description>nn2这个NameNode对外提供的http服务的端口</description>
    </property>
    <property>
          	 <name>dfs.namenode.shared.edits.dir</name>
             <value>qjournal://master:8485;slave1:8485;slave2:8485/mycluster</value>
    		 <description>标识Journal组</description>
     </property>
     <property>
             <name>dfs.journalnode.edits.dir</name>
             <value>/home/hadoop-jrq/bigdata/dfs/journal/data</value>
             <description>存储Journal数据的地方</description>
     </property>
     <property>
             <name>dfs.client.failover.proxy.provider.mycluster</name>
             <value>org.apache.hadoop.hdfs.server.namenode.ha.ConfiguredFailoverProxyProvider</value>
     		<description>用于Java客户端来连接Active的nameNode</description>
     </property>
     <property>
                <name>dfs.ha.fencing.methods</name>
                <value>sshfence</value>
                <description>用于在nameNode失败的时候不会对外提供服务</description>
      </property>
       <property>
               <name>dfs.ha.fencing.ssh.private-key-files</name>
               <value>/home/hadoop-jrq/.ssh/id_dsa</value>
       <description>用于在nameNode失败的时候不会对外提供服务</description>
       </property>
用hadoop-jrq账号在slave1上配置无密钥登陆master:
ssh-keygen -t dsa -P '' -f ~/.ssh/id_dsa
cat ~/.ssh/id_dsa.pub >> ~/.ssh/authorized_keys
scp ~/.ssh/authorized_keys hadoop-jrq@master:~/.ssh/
ssh master不需要密码就表示配置成功
用root用户在master和slave1上安装fuser:
	yum -y install psmisc

配置core-site.xml

<property>
         	 <name>fs.defaultFS</name>
              <value>hdfs://mycluster</value>
			<description>HDFS的基本路径,这个路径可以随意写</description>
 </property>
将core-site.xml hdfs-site.xml同步到到slave1和slave2上:
scp core-site.xml hdfs-site.xml hadoop-jrq@slave1:~/bigdata/hadoop-2.7.5/etc/hadoop/
scp core-site.xml hdfs-site.xml hadoop-jrq@slave2:~/bigdata/hadoop-2.7.5/etc/hadoop/
在master、slave1和slave2上执行~/bigdata/hadoop-2.7.5/sbin/hadoop-daemon.sh start journalnode
在master中执行scp -r ~/bigdata/dfs/name/ hadoop-jrq@slave1:~/bigdata/dfs/
1
1.如果从一个不是HA的HDFS集群转向HA集群,那么执行:(为了同步数据)
	在slave1中执行~/bigdata/hadoop-2.7.5/bin/hdfs namenode -bootstrapStandby => 同步两个namenode的数据
	(上面这步可以不做)
	在master中执行hdfs namenode -initializeSharedEdits => 初始化journal node的数据
2.如果是全新的搭建一个HA的HDFS集群,那么执行:
	在master中执行hdfs namenode -format即可

重启HDFS集群

start-dfs.sh

手动控制nameNode的状态

hdfs haadmin -getServiceState nn1 => 查看nn1这个nameNode的状态
hdfs haadmin -transitionToStandby nn1 => 将nn1设置为standby状态
hdfs haadmin -transitionToActive nn1 => 将nn1设置为active状态

配置自动状态改变

显然手动控制状态在生产上市不行的,因此需要其自动的去改变状态

先要stop-dfs.sh, 然后启动zookeeper集群

配置master上的hdfs-site.xml

<property>
 		 <name>dfs.ha.automatic-failover.enabled</name>
         <value>true</value>
  </property>

配置master上的core-site.xml

<property>
   <name>ha.zookeeper.quorum</name>
   <value>master:2181,slave1:2181,slave2:2181</value>
</property>
将core-site.xml hdfs-site.xml同步到到slave1和slave2上:
scp core-site.xml hdfs-site.xml hadoop-jrq@slave1:~/bigdata/hadoop-2.7.5/etc/hadoop/
scp core-site.xml hdfs-site.xml hadoop-jrq@slave2:~/bigdata/hadoop-2.7.5/etc/hadoop/

在master中执行~/bigdata/hadoop-2.7.5/bin/hdfs zkfc -formatZK   (目的是为了在zk中创建节点,记录数据)
在master中执行start-dfs.sh
验证 http://master:50070,http://slave1:50070,hadoop fs -ls hdfs://mycluster/

注意

1.在执行上述步骤时,zk集群必须是启动状态,否则会报错连接不上集群,也启动不了集群
2.配置了高可用的集群,在写代码的时候不能用hdfs://master:8020的方式去访问了,因为如果你的master或者slave1其中一个挂了呢,这时候你用这种方式去写死,就会直接报错,因此,配置了高可用的集群,写代码的时候需要这么写:hdfs://mycluster/ 用这个来代替,也就是上面的fs.defaultFS的值

杀死一个active状态的namenode进行验证

杀死active的namenode看看namenode的active是否会转换:
hadoop-daemon.sh stop namenode

恢复成非HA状态(NameNode放在master)

stop-dfs.sh

备份ha的配置

mv hdfs-site.xml hdfs-site.xml_ha
mv core-site.xml core-site.xml_ha

还原非ha的配置

mv hdfs-site.xml_bak hdfs-site.xml
mv core-site.xml_bak core-site.xml

将配置同步到slave1和slave2

scp hdfs-site.xml core-site.xml hadoop-jrq@slave1:~/bigdata/hadoop-2.7.5/etc/hadoop/
scp hdfs-site.xml core-site.xml hadoop-jrq@slave2:~/bigdata/hadoop-2.7.5/etc/hadoop/

同步master上journalNode中的edits log到master的NameNode所管理的edits log目录(注意不要覆盖) 因为你的日志有可能在master上没有,因此启动时会报错,namenode启动不了,所以需要将日志同步过去,并且不能覆盖
cp -i ~/bigdata/dfs/journal/data/mycluster/current/edits_0* ~/bigdata/dfs/name/current/

start-dfs.sh

删除zookeeper上的相关数据

zkCli.sh
delete /hadoop-ha/mycluster/ActiveBreadCrumb
delete /hadoop-ha/mycluster
delete /hadoop-ha

删除journalNode管理的数据

分别在master、slave1以及slave2上执行:
rm -r ~/bigdata/dfs/journal/*

删除slave1上NameNode管理的数据

在slave1上执行:
rm -r ~/bigdata/dfs/name/*
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值