Hadoop+Zookeeper
实验背景:
-
在典型的 HA 集群中,通常有两台不同的机器充当 Namenode(在接下来简称为NN)。在任何时间,只有一台机器处于Active 状态;另一台机器是处于 Standby 状态。Active NN 负责集群中所有客户端的操作;而 Standby NN 主要用于备用,它主要维持足够的状态,如果必要,可以提供快速的故障恢复。
-
为了让 Standby NN 的状态和 Active NN 保持同步,即元数据保持一致,它们都将会JournalNodes 守护进程通信。当 Active NN 执行任何有关命名空间的修改,它需要持久化到一半以上的JournalNodes 上(通过 edits log 持久化存储),而 Standby NN 负责观察edits log的变化,它能够读取从 JNs 中读取 edits 信息,并更新其内部的命名空间。一旦 Active NN出现故障,Standby NN 将会保证从 JNs 中读出了全部的 Edits,然后切换成 Active 状态。Standby NN 读取全部的 edits 可确保发生故障转移之前,是和 Active NN 拥有完全同步的命名空间状态。
-
为了提供快速的故障恢复,Standby NN 也需要保存集群中各个文件块的存储位置。为了实现这个,集群中所有的 Database 将配置好 Active NN 和 Standby NN 的位置,并向它们发送块文件所在的位置及心跳,如下图所示:
-
在任何时候,集群中只有一个NN处于Active 状态是极其重要的。否则,在两个Active NN的状态下 NameSpace 状态将会出现分歧,这将会导致数据的丢失及其它不正确的结果。为了保证这种情况不会发生,在任何时间,JNs 只允许一个 NN 充当 writer。在故障恢复期间,将要变成 Active 状态的NN 将取得 writer 的角色,并阻止另外一个 NN 继续处于 Active状态。
-
为了部署 HA 集群,需要准备以下事项:
- 1.NameNode machines:运行 Active NN 和 Standby NN 的机器需要相同的硬件配置;
- 2.JournalNode machines:也就是运行 JN 的机器。JN 守护进程相对来说比较轻量,所以这些守护进程可以可其他守护线程(比如 NN,YARN ResourceManager)运行在同一台机器上。在一个集群中,最少要运行 3 个 JN 守护进程,这将使得系统有一定的容错能力。当然,你也可以运行 3 个以上的 JN,但是为了增加系统的容错能力,你应该运行奇数个 JN(3、5、7 等),当运行 N 个 JN,系统将最多容忍(N-1)/2 个 JN 崩溃;
- 3.在 HA 集群中,Standby NN 也执行 namespace 状态的 checkpoints,所以不必要运行Secondary NN、CheckpointNode 和 BackupNode;事实上,运行这些守护进程是错误的。
ZooKeeper简介
- 它是一个分布式的,开放源码的分布式应用程序协调服务,是Google的Chubby一个开源的实现,是Hadoop和Hbase的重要组件;
- 它是一个为分布式应用提供一致性服务的软件,提供的功能包括:配置维护、域名服务、分布式同步、组服务等;
- ZooKeeper的目标就是封装好复杂易出错的关键服务,将简单易用的接口和性能高效、功能稳定的系统提供给用户;
- ZooKeeper包含一个简单的原语集,提供Java和C的接口。
实验环境:
主机 | 角色 |
---|---|
server2 | NameNode DFSZKFailoverController ResourceManager |
server3 | JournalNode QuorumPeerMain DataNode NodeManager |
server4 | JournalNode QuorumPeerMain DataNode NodeManager |
server5 | JournalNode QuorumPeerMain DataNode NodeManager |
server6 | NameNode(新添加的) DFSZKFailoverController ResourceManager |
部署过程:
- 步骤一:在server2、server3、server4、server5上删除
/tmp/*
内容,然后再新添加的server6上创建用户bdkl,安装nfs,挂载server2的/home/bdkl到本地的/home/bdkl下
- 步骤二:安装zookeeper,并进行配置
接下来在server6上对zookeeper进行设置,各节点配置文件相同,并且需要在/tmp/zookeeper 目录中创建 myid 文件,写入一个唯一的数字,取值范围在 1-255。比如:192.168.0.102 节点的 myid 文件写入数字“1”,此数字与配置文件中的定义保持一致,其它节点依次类推,配置文件不用再每个节点更改,只需要改myid,因为nfs已经进行共享了/home/bdkl/*
server.x=[hostname]:nnnnn[:nnnnn]
注意:这里的 x 是一个数字,与 myid 文件中的 id 是一致的。右边可以配置两个端口,第一个端口用于 F 和 L 之间的数据同步和其它通信,第二个端口用于 Leader 选举过程中投票通信。
- 步骤三:在三个datanode上创建myid文件,并且启动进程
接下来在三台datanode上启动zookeeper进程,并查看状态
注意:要先在三台datanode上启动进程,然后再依次查看状态
- 步骤四:server2和server6做的Hadoop高可用的master,接下来在其上做相关配置
先测试一下server2对server6的免密登录
编辑控制 hdfs的文件
1、指定 hdfs 的 nameservices 为 masters,和 core-site.xml 文件中的设置保持一致
<property>
<name>dfs.nameservices</name>
<value>masters</value>
</property>
2、 masters 下面有两个 namenode 节点,分别是 h1 和 h2 (名称可自定义)
<property>
<name>dfs.ha.namenodes.masters</name>
<value>h1,h2</value>
</property>
3、指定 h1 节点的 rpc 通信地址
<property>
<name>dfs.namenode.rpc-address.masters.h1</name>
<value>192.168.0.102:9000</value>
</property>
4、指定 h1 节点的 http 通信地址,这是web界面的通信地址
<property>
<name>dfs.namenode.http-address.masters.h1</name>
<value>192.168.0.102:9870</value>
</property>
5、指定 h2 节点的 rpc 通信地址
<property>
<name>dfs.namenode.rpc-address.masters.h2</name>
<value>192.168.0.106:9000</value>
</property>
6、指定 h2 节点的 http 通信地址
<property>
<name>dfs.namenode.http-address.masters.h2</name>
<value>192.168.0.106:9870</value>
</property>
7、指定 NameNode 元数据在 JournalNode 上的存放位置,在是个datanode上
<property>
<name>dfs.namenode.shared.edits.dir</name>
<value>qjournal://192.168.0.103:8485;192.168.0.104:8485;192.168.0.105:8485/masters</value>
</property>
8、指定 JournalNode 在本地磁盘存放数据的位置
<property>
<name>dfs.journalnode.edits.dir</name>
<value>/tmp/journaldata</value>
</property>
9、开启 NameNode 失败自动切换
<property>
<name>dfs.ha.automatic-failover.enabled</name>
<value>true</value>
</property>
10、配置失败自动切换实现方式
<property>
<name>dfs.client.failover.proxy.provider.masters</name>
<value>org.apache.hadoop.hdfs.server.namenode.ha.ConfiguredFailoverProxyProvider</value>
</property>
11、配置隔离机制方法,每个机制占用一行
<property>
<name>dfs.ha.fencing.methods</name>
<value>
sshfence
shell(/bin/true)
</value>
</property>
12、使用 sshfence 隔离机制时需要 ssh 免密码
<property>
<name>dfs.ha.fencing.ssh.private-key-files</name>
<value>/home/bdkl/.ssh/id_rsa</value>
</property>
13、配置 sshfence 隔离机制超时时间
<property>
<name>dfs.ha.fencing.ssh.connect-timeout</name>
<value>30000</value>
</property>
- 步骤五:启动HDFS集群(需要按照下面的顺序依次启动)
首先在三个datanode上依次启动 zookeeper 集群
然后在三个datanode上依次启动 journalnode
格式化 HDFS 集群
格式化 zookeeper (只需在 h1 上执行即可)
启动hdfs集群(只需在 h1 上执行即可)
- 步骤六:测试
恢复server2的namenode
注意:在恢复时,不能够再调用脚本来启动,而是需要用命令来进行启动
yarn的高可用
首选配置mapred-site.xml 文件
<configuration>
<!-- 指定 yarn 为 MapReduce 的框架 -->
<property>
<name>mapreduce.framework.name</name>
<value>yarn</value>
</property>
</configuration>
然后再编辑 yarn-site.xml 文件
<configuration>
<!-- 配置可以在 nodemanager 上运行 mapreduce 程序 -->
<property>
<name>yarn.nodemanager.aux-services</name>
<value>mapreduce_shuffle</value>
</property>
<!-- 激活 RM 高可用 -->
<property>
<name>yarn.resourcemanager.ha.enabled</name>
<value>true</value>
</property><!-- 指定 RM 的集群 id -->
<property>
<name>yarn.resourcemanager.cluster-id</name>
<value>RM_CLUSTER</value>
</property>
<!-- 定义 RM 的节点-->
<property>
<name>yarn.resourcemanager.ha.rm-ids</name>
<value>rm1,rm2</value>
</property>
<!-- 指定 RM1 的地址 -->
<property>
<name>yarn.resourcemanager.hostname.rm1</name>
<value>192.168.0.102</value>
</property>
<!-- 指定 RM2 的地址 -->
<property>
<name>yarn.resourcemanager.hostname.rm2</name>
<value>192.168.0.106</value>
</property>
<!-- 激活 RM 自动恢复 -->
<property>
<name>yarn.resourcemanager.recovery.enabled</name>
<value>true</value>
</property>
<!-- 配置 RM 状态信息存储方式,有 MemStore 和 ZKStore-->
<property>
<name>yarn.resourcemanager.store.class</name>
<value>org.apache.hadoop.yarn.server.resourcemanager.recovery.ZKRMStateStore</
value>
</property>
<!-- 配置为 zookeeper 存储时,指定 zookeeper 集群的地址 -->
<property>
<name>yarn.resourcemanager.zk-address</name>
<value>192.168.0.103:2181,192.168.0.104:2181,192.168.0.105:2181</value>
</property>
</configuration>
测试将server2的ResourceManager进程杀掉,server6是否变为active
恢复server2的ResourceManager进程