四、HADOOP(HDFS)-08
HDFS HA 高可用
1、HA 概述
1)所谓 HA(High Available),即高可用(7*24 小时不中断服务)。
2)实现高可用最关键的策略是消除单点故障。HA 严格来说应该分成各个组件的 HA 机制:
HDFS 的 HA 和 YARN 的 HA。
3)Hadoop2.0 之前,在 HDFS 集群中 NameNode 存在单点故障(SPOF)。
4)NameNode 主要在以下两个方面影响 HDFS 集群
NameNode 机器发生意外,如宕机,集群将无法使用,直到管理员重启
NameNode 机器需要升级,包括软件、硬件升级,此时集群也将无法使用
HDFS HA 功能通过配置 Active/Standby 两个 NameNodes 实现在集群中对 NameNode 的
热备来解决上述问题。如果出现故障,如机器崩溃或机器需要升级维护,这时可通过此种方式将 NameNode 很快的切换到另外一台机器。
2、HDFS-HA 工作机制
通过双NameNode消除单点故障
3、HDFS-HA 重点
1、元数据管理方式需要改变
内存中各自保存一份元数据;
Edits日志只有Active状态的NameNode节点可以做写操作;
两个NameNode都可以读取Edits;
共享的Edits放在一个共享储存管理(qjournal和NFS两个主流实现);
2、需要一个状态管理功能模块
实现了一个zkfailover,常驻在每一个NameNode所在的节点,每一个zkfailove负责监控自己所在NameNode节点,利用zk进行状态标识,当需要进行状态切换时,由zkfailover来负责切换,切换时需要防止 brain split(脑裂)现象的发生。
3、必须保证两个NameNode之间能够ssh免密钥登录
4、隔离(fence),即同时刻仅有一个NameNode 对外提供服务
4、HDFS-HA 自动故障转移工作机制
1、故障检测
集群中的每个 NameNode 在 ZooKeeper 中维护了一个持久会话,如果
机器崩溃,ZooKeeper 中的会话将终止,ZooKeeper 通知另一个 NameNode 需要触发故障转移。
2、现役NameNode 选择
ZooKeeper 提供了一个简单的机制用于唯一的选择一个节点为 active 状态。如果目前现役 NameNode 崩溃,另一个节点可能从 ZooKeeper 获得特殊的排外锁以表明它应该成为现役 NameNode。
另外,ZKFC 是自动故障转移中的另一个新组件,是 ZooKeeper 的客户端,也监视和管理NameNode 的状态。每个运行 NameNode 的主机也运行了一个 ZKFC 进程,ZKFC 负责。
3、健康监测
ZKFC 使用一个健康检查命令定期地 ping 与之在相同主机的 NameNode,只要该 NameNode 及时地回复健康状态,ZKFC 认为该节点是健康的。如果该节点崩溃,冻结或进入不健康状态,健康监测器标识该节点为非健康的。
4、Zookeeper 会话管理
当本地 NameNode 是健康的,ZKFC 保持一个在 ZooKeeper中打开的会话。如果本地 NameNode 处于 active 状态,ZKFC 也保持一个特殊的 znode 锁,该锁使用了 ZooKeeper 对短暂节点的支持,如果会话终止,锁节点将自动删除。
5、基于Zookeeper的选择
如果本地 NameNode 是健康的,且 ZKFC 发现没有其它的节点当前持有 znode 锁,它将为自己获取该锁。如果成功,则它已经赢得了选择,并负责运行故障转移进程以使它的本地 NameNode 为 Active。故障转移进程与前面描述的手动故障转移相似,首先如果必要保护之前的现役 NameNode,然后本地 NameNode 转换为 Active 状态。
5、HDFS-HA集群的搭建
1、环境准备
(1) 修改 IP
(2) 修改主机名及主机名和IP地址的映射
(3) 关闭防火墙
(4) ssh免密钥
(5) 安装 JDK、配置环境变量等
2、集群规划
hadoop102 | hadoop103 | hadoop104 |
---|---|---|
NameNode | NameNode | |
JournalNode | JournalNode | JournalNode |
ZK | ZK | ZK |
ResourceManager | ||
NodeManager | NodeManager | NodeManager |
3、Zookeeper集群配置
1、集群规划
在 hadoop102、hadoop103 和 hadoop104 三个节点上部署 Zookeeper。
2、解压安装
(1) 解压 Zookeeper 安装包到/opt/module/目录下
[lyinl@hadoop102 software]$ tar -zxvf zookeeper-3.4.10.tar.gz -C /opt/module/
(2) 在/opt/module/zookeeper-3.4.10/这个目录下创建 zkData
mkdir -p zkData
(3) 重命名/opt/module/zookeeper-3.4.10/conf 这个目录下的zoo_sample.cfg 为 zoo.cfg.
mv zoo_sample.cfg zoo.cfg
3、配置zoo.cfg文件
(1) 配置数据输出路径
dataDir=/opt/module/zookeeper-3.4.10/zkData
然后在文件最后增加如下配置
#######################cluster##########################
server.2=hadoop102:2888:3888
server.3=hadoop103:2888:3888
server.4=hadoop104:2888:3888
(2) 配置参数解读
Server.A=B:C:D
A 是一个数字,表示这个是第几号服务器;
B 是这个服务器的 IP 地址;
C 是这个服务器与集群中的 Leader 服务器交换信息的端口;
D 是万一集群中的 Leader 服务器挂了,需要一个端口来重新进行选举,选出一个新的Leader,而这个端口就是用来执行选举时服务器相互通信的端口。
集群模式下配置一个文件 myid,这个文件在 dataDir 目录下,这个文件里面有一个数据就是 A 的值,Zookeeper 启动时读取此文件,拿到里面的数据与 zoo.cfg 里面的配置信息比较从而判断到底是哪个 server。
4、集群操作
(1) 在/opt/module/zookeeper-3.4.10/zkData 目录下创建一个 myid 的文件
touch myid
注意 添加 myid 文件,注意一定要在 linux 里面创建,在 notepad++里面很可能乱码*
(2) 编辑myid文件
vi myid
在文件中添加与server对应的编号:如 2
(3) 拷贝配置好的zookeeper到其他机器上
scp -r zookeeper-3.4.10/ root@hadoop103.lyinl.com:/opt/app/
scp -r zookeeper-3.4.10/ root@hadoop104.lyinl.com:/opt/app/
并分别修改 myid 文件中内容为 3、4
(4) 分别启动zookeeper
[root@hadoop102 zookeeper-3.4.10]# bin/zkServer.sh start
[root@hadoop103 zookeeper-3.4.10]# bin/zkServer.sh start
[root@hadoop104 zookeeper-3.4.10]# bin/zkServer.sh start
(5) 查看zookeeper状态
[root@hadoop102 zookeeper-3.4.10]# bin/zkServer.sh status
JMX enabled by default
Using config: /opt/module/zookeeper-
3.4.10/bin/../conf/zoo.cfg
Mode: follower
[root@hadoop103 zookeeper-3.4.10]# bin/zkServer.sh status
JMX enabled by default
Using config: /opt/module/zookeeper-
3.4.10/bin/../conf/zoo.cfg
Mode: leader
[root@hadoop104 zookeeper-3.4.5]# bin/zkServer.sh status
JMX enabled by default
Using config: /opt/module/zookeeper-
3.4.10/bin/../co
4、HDFS-HA集群配置
1、官方地址:http://hadoop.apache.org/
2、在opt目录下创建一个ha文件夹
mkdir ha
3、将/opt/app/下的 hadoop-2.7.2 拷贝到/opt/ha 目录下
cp -r hadoop-2.7.2/ /opt/ha/
4、配置Hadoop-env.sh
export JAVA_HOME=/opt/module/jdk1.8.0_144
5、配置core-site.xml
<configuration>
<!-- 把两个 NameNode)的地址组装成一个集群 mycluster -->
<property>
<name>fs.defaultFS</name>
<value>hdfs://mycluster</value>
</property>
<!-- 指定 hadoop 运行时产生文件的存储目录 -->
<property>
<name>hadoop.tmp.dir</name>
<value>/opt/ha/hadoop-2.7.2/data/tmp</value>
</property>
</configuration>
6、配置hdfs-site.xml
<configuration>
<!-- 完全分布式集群名称 -->
<property>
<name>dfs.nameservices</name>
<value>mycluster</value>
</property>
<!-- 集群中 NameNode 节点都有哪些 -->
<property>
<name>dfs.ha.namenodes.mycluster</name>
<value>nn1,nn2</value>
</property>
<!-- nn1 的 RPC 通信地址 -->
<property>
<name>dfs.namenode.rpc-address.mycluster.nn1</name>
<value>hadoop102:9000</value>
</property>
<!-- nn2 的 RPC 通信地址 -->
<property>
<name>dfs.namenode.rpc-address.mycluster.nn2</name>
<value>hadoop103:9000</value>
</property>
<!-- nn1 的 http 通信地址 -->
<property>
<name>dfs.namenode.http-address.mycluster.nn1</name>
<value>hadoop102:50070</value>
</property>
<!-- nn2 的 http 通信地址 -->
<property>
<name>dfs.namenode.http-address.mycluster.nn2</name>
<value>hadoop103:50070</value>
</property>
<!-- 指定 NameNode 元数据在 JournalNode 上的存放位置 -->
<property>
<name>dfs.namenode.shared.edits.dir</name>
<value>qjournal://hadoop102:8485;hadoop103:8485;hadoop10
4:8485/mycluster</value>
</property>
<!-- 配置隔离机制,即同一时刻只能有一台服务器对外响应 -->
<property>
<name>dfs.ha.fencing.methods</name>
<value>sshfence</value>
</property>
<!-- 使用隔离机制时需要 ssh 无秘钥登录-->
<property>
<name>dfs.ha.fencing.ssh.private-key-files</name>
<value>/home/atguigu/.ssh/id_rsa</value>
</property>
<!-- 声明 journalnode 服务器存储目录-->
<property>
<name>dfs.journalnode.edits.dir</name>
<value>/opt/ha/hadoop-2.7.2/data/jn</value>
</property>
<!-- 关闭权限检查-->
<property>
<name>dfs.permissions.enable</name>
<value>false</value>
</property>
<!-- 访问代理类:client,mycluster,active 配置失败自动切换实现方
式-->
<property>
<name>dfs.client.failover.proxy.provider.mycluster</name
>
<value>org.apache.hadoop.hdfs.server.namenode.ha.Configu
redFailoverProxyProvider</value>
</property>
</configuration>
7、将Hadoop拷贝到其他节点
5、启动HDFS-HA集群
1、在各个 JournalNode 节点上,输入以下命令启动 journalnode 服务
sbin/hadoop-daemon.sh start journalnode
2、在[nn1]上,对其进行格式化,并启动
bin/hdfs namenode -format
sbin/hadoop-daemon.sh start namenode
3、在[nn2]上,同步 nn1 的元数据信息
bin/hdfs namenode -bootstrapStandby
4、启动[nn2]
sbin/hadoop-daemon.sh start namenode
5、查看 web 页面显示:
6、在[nn1]上,启动所有 datanode
sbin/hadoop-daemons.sh start datanode
7、将[nn1]切换为 Active
bin/hdfs haadmin -transitionToActive nn1
8、查看是否 Active
bin/hdfs haadmin -getServiceState nn1
6、配置HDFS-HA自动故障转移
1、具体配置
(1) 在 hdfs-site.xml 中增加
<property>
<name>dfs.ha.automatic-failover.enabled</name>
<value>true</value>
</property>
(2) 在 core-site.xml 文件中增加
<property>
<name>ha.zookeeper.quorum</name>
<value>hadoop102:2181,hadoop103:2181,hadoop104:2181</value>
</property>
2、启动
(1) 关闭所有HDFS服务:
sbin/stop-dfs.sh
(2) 启动zookeeper集群:
bin/zkServer.sh start
(3) 初始化HA 在Zookeeper中状态
bin/hdfs zkfc -formatZK
(4) 启动HDFS服务:
sbin/start-dfs.sh
(5) 在各个 NameNode 节点上启动 DFSZK Failover Controller,先在哪台机器启动,哪个机器的 NameNode 就是 Active NameNode。
sbin/hadoop-daemin.sh start zkfc
3、验证
(1) 将Active NameNode进程kill
kill -9 namenode 的进程 id
(2) 将Active NameNode 机器断开网络
service network stop
7、YARN-HA配置
1、YARN-HA工作机制
1、官方文档:
http://hadoop.apache.org/docs/r2.7.2/hadoop-yarn/hadoop-yarn-site/ResourceManagerHA.html
2、YARN-HA工作机制,如图:
2、配置YARN-HA集群
1、环境准备
(1)修改 IP
(2)修改主机名及主机名和 IP 地址的映射
(3)关闭防火墙
(4)ssh 免密登录
(5)安装 JDK,配置环境变量等
(6)配置 Zookeeper 集群
2、集群规划
Hadoop102 | Hadoop103 | Hadoop104 |
---|---|---|
NameNode | NameNode | |
JournalNode | JournalNode | JournalNode |
DataNode | DataNode | DataNode |
ZK | ZK | ZK |
ResourceManager | ResourceManage | |
NodeManage | NodeManage | NodeManage |
3、配置文件
(1) yarn-site.xml
<configuration>
<property>
<name>yarn.nodemanager.aux-services</name>
<value>mapreduce_shuffle</value>
</property>
<!--启用 resourcemanager ha-->
<property>
<name>yarn.resourcemanager.ha.enabled</name>
<value>true</value>
</property>
<!--声明两台 resourcemanager 的地址-->
<property>
<name>yarn.resourcemanager.cluster-id</name>
<value>cluster-yarn1</value>
</property>
<property>
<name>yarn.resourcemanager.ha.rm-ids</name>
<value>rm1,rm2</value>
</property>
<property>
<name>yarn.resourcemanager.hostname.rm1</name>
<value>hadoop102</value>
</property>
<property>
<name>yarn.resourcemanager.hostname.rm2</name>
<value>hadoop103</value>
</property>
<!--指定 zookeeper 集群的地址-->
<property>
<name>yarn.resourcemanager.zk-address</name>
<value>hadoop102:2181,hadoop103:2181,hadoop104:2181</value
>
</property>
<!--启用自动恢复-->
<property>
<name>yarn.resourcemanager.recovery.enabled</name>
<value>true</value>
</property>
<!--指定 resourcemanager 的状态信息存储在 zookeeper 集群-->
<property>
<name>yarn.resourcemanager.store.class</name>
<value>org.apache.hadoop.yarn.server.resourcemanager.recov
ery.ZKRMStateStore</value>
</property>
</configuration>
(2) 同步更新其他节点的配置
4、启动hdfs
(1) 在各个journalNode节点上,输入以下命令启动journalnode服务:
sbin/hadoop-daemon.sh start journalnode
(2) 在[nn1]上,对其进行格式化,并启动:
bin/hdfs namenode -format
sbin/hadoop-daemon.sh start namenode
(3) 在[nn2]上,同步nn1的元数据信息:
bin/hdfs namenode -bootstrapStandby
(4) 启动[nn2]:
sbin/hadoop-daemon.sh start namenode
(5) 启动所有DataNode
sbin/hadoop-daemons.sh start datanode
(6) 将[nn1]切换为Active
sbin/hadoop-daemons.sh start datanode
5、启动YARN
(1) 在Hadoop102中执行:
sbin/start-yarn.sh
(2) 在Hadoop103中执行:
sbin/yarn-daemon.sh start resourcemanager
(3) 查看服务状态:
bin/yarn rmadmin -getServiceState rm1
8、HDFS Federation架构设计
1、NameNode架构的局限性
(1) Namespace(命名空间)的限制
由于NameNode在内存中存储所有的元数据(metadata),因此单个NameNode所能存储的对象(文件+块)数目受到NameNode所在JVM的heap size的限制。50G的heap能够存储20亿(200million)个对象,这20亿个对象支持4000个DataNode,12PB的储存(假设文件平均大小为40MB)。随着数据的飞速增长,储存的需求也随之增长。单个DataNode从4T增长到36T,集群的尺寸增长到8000个DataNode。存储的需求从12PB增长到大于100PB。
(2) 隔离问题
由于HDFS仅有一个NameNode,无法隔离各个程序,因此HDFS上的一个实验程序就有可能影响整个HDFS上运行程序。
(3) 性能的瓶颈
由于是单个NameNode的HDFS架构,因此HDFS文件系统的吞吐量受限制于单个NameNode 的吞吐量。
2、HDFS Federation 架构设计,如图示:
NameNode | NameNode | NameNode |
---|---|---|
元数据 | 元数据 | 元数据 |
Log | machine | 真实数据 |
3、HDFS Federation应用
不同应用可以使用不同 NameNode 进行数据管理图片业务、爬虫业务、日志审计业务Hadoop 生态系统中,不同的框架使用不同的 NameNode 进行管理 NameSpace。(隔离性)