刚经过一个阶段的大数据学习,详细的记录了一下搭建Hadoop HA 高可用集群的全过程━(`∀´)ノ亻找bug的过程好心酸啊,但学习到新知识还是感觉好开心hhhh
你是真的真的真的真的真的很不错 !
hadoop 1.x是由分布式计算框架MapReduce和分布式存储系统HDFS两个分支构成的。其中HDFS由一个Namenode和多个DateNode组成。只有一个Namenode,所有元数据由唯一的Namenode负责管理,可想而之,当这个NameNode挂掉时,整个集群基本也就不可用了。
Hadoop 2.x由HDFS、MapReduce和YARN三个分支构成。在 1.x 版本的基础上,提出HDFS Federation,并引入资源管理框架Yarn,负责集群资源管理和调度。HA机制也是从hadoop2.0开始,之前的版本中并没有HA机制,HDFS的HA机制通过引入双NameNode架构( NN Federation联邦),每个NameNode管理不同文件的元数据,解决了单点故障问题,实现HDFS 的高可用。
所谓HA,即高可用(7*24小时不中断服务),实现高可用最关键的是消除单点故障。hadoop-ha严格来说应该分成各个组件的HA机制——HDFS的HA、YARN的HA
HDFS 的HA机制 2.x ,解决了HDFS 1.x 中 单点故障和 内存受限问题
解决单点故障:
•主备NameNode(如果主NameNode发生故障,则切换到备NameNode上)
--主NameNode对外提供服务,备NameNode同步主元数据,以待切换
--所有DataNode同时向两个汇报数据块信息
解决内存受限问题:
•HDFS Federation(联邦)
•水平扩展,支持多个NameNode;
--每个NameNode分管一部分目录,把单个namenode的负载分散到多个节点中,把不同类型应用的HDFS元数据的存储和管理分派到不同的namenode中。
--所有NameNode共享所有DataNode存储资源
主NameNode和备NameNode之间的切换:
•手动切换 :通过命令实现主备之间的切换。
•基于Zookeeper的自动切换 :
--ZooKeeper Failover Controller:监控NameNode健康状态,部署在每个NameNode的节点上,作为一个demon进程,它会周期性的向它监控的NN发送健康探测命令,从而来确定某个NameNode是否处于健康状态,如果机器宕机,心跳失败,那么zkfc就会标记它处于一个不健康的状态如果NN是健康的,zkfc就会在zookeeper中保持一个打开的会话,如果NameNode同时还是Active状态的,那么zkfc还会在Zookeeper中占有一个类型为短暂类型的znode, 当这个NN挂掉时,这个znode将会被删除,然后备用的NN,将会得到这把锁,升级为主NN,同时标记状态为Active。当宕机的NN新启动时,它会再次注册zookeper,发现已经有znode锁了,便会自动变为Standby状态,如此往复循环,保证高可靠。
ZKFC为NameNode竞争锁,获得ZKFC 锁的NameNode变为active。如上就涉及到了master选举,通过在zookeeper中维持一个短暂类型的znode,来实现抢占式的锁机制,从而判断那个NameNode为Active状态。
HA 架构图
配置:
VMware Workstation Pro (安装好CentOS-6.5 的linux操作系统)
纯净版虚拟机(CentOS 6 64位)
通过克隆 CentOS 6 64位 虚拟机,得到四台虚拟机CentOS-node01,02,03,04 ,如下图:
HA安装方案
接下来我们将利用VMware搭建四个节点的集群hadoop,其各个节点分布如下:(将严格按照以下安装方案)
*带星的地方表示该台机子上需要安装该配置
命令:
vi /etc/sysconfig/network-scripts/ifcfg-eth0
配置情况如下:
执行:service network restart
重启网络服务命令,要出来如下图全是OK,则配置成功
测试:ping www.baidu.com
ping一下百度,看下是否成功
成功则一直在加载64 bytes …的语句,按 CTRL+C停止加载
命令:
vi /etc/sysconfig/network
命令:
vi /etc/hosts
配置情况如下:
我们是配置四台机子的集群,所以在下面添加了四台机子的信息,由上也可以看出,四台机子分别的子网IP是多少。
关机命令:poweroff
给CentOS-node01关机,拍摄快照,存一个非常干净的Linux版本。
走完所有的安装过程,我总结,一定要有拍摄快照这个好习惯,关键时候能起到很大的作用呢 !
1.给CentOS-node02配置,配置过程同给CentOS-node01配置
该机子IP配置如下:
*注意红圈,node01 为31 ;node02 为32 ;node03 为33 ;node04为 34
2.配置完CentOS-node02 ,两台机子互相ping一下看是否能ping通
具体操作:
在 CentOS-node01 中输入命令: ping CentOS-node02
在CentOS-node02 中输入命令: ping CentOS-node01
能ping通则指两台机子彼此之间可以访问
3.将余下的CentOS-node03 和CentOS-node04 都配置好
配置过程一定要仔细,不要直接复制网页命令,自己动手敲敲吧
4.使四台机子彼此之间都能访问
5.让windows和虚拟机之间也能访问
修改Windows上的hosts文件
路径 : C:/Windows/System32/drivers/etc
用Notepad++ 或什么都可以,只要能打开软件对其进行修改保存
我这里是用Notepad++ 打开的文档,在最后添加和上面一样的四台机子的信息
*Notepad++修改保存时,点击保存后,该页面会刷新一下,需再次点击保存才是真的保存好了
xftp 软件 是一个基于 MS windows 平台的功能强大的SFTP、FTP 文件传输软件。使用了 Xftp 以后,MS windows 用户能安全地在 UNIX/Linux 和 Windows PC 之间传输文件。 直接搜索xftp安装压缩包,傻瓜式安装即可。
xshell 软件 是一个终端模拟软件,而且是远程近程都可以。 就是模拟服务器所在的linux,在xshell中可以输入命令, 就像在服务器的linux中输入命令一样。一般用于远程 连接。在本次安装过程中我将会使用xshell连接虚拟机进行操作,免去了鼠标在windows和linux之间来回切换的不便性。
也可直接在xshell命令打开xftp软件,在windows和linux之间进行文件的传输。
也会用到下面的xshell的全部会话框去输命令,避免重复在每个机子上都要输一次命令
使用rpm命令进行安装 (rpm相当于windows里的exe文件)
rpm -i jdk-7u67-linux-x64.rpm
whereis java //查看java的存放路径
vi + /etc/profile //修改etc下的profile如下图
source /etc/profile
source一下,刷新该文件。
如果出现-bash: jps: command not found 改: export JAVA_HOME=/usr/bin/java
export PATH=$PATH:/usr/java/jdk1.7.0_67/bin
在家目录下 , ll -a
看有无**.ssh**文件
若无,则先 ssh localhost
一下 (每次ssh登录 ,都别忘了要exit)
ssh-keygen -t dsa -P '' -f ~/.ssh/id_dsa //生成密钥
cat ~/.ssh/id_dsa.pub >> ~/.ssh/authorized_keys
//把id_dsa.pub 追加到 ~/.ssh/authorized_keys 下
ssh localhost //验证是否仍需要密码登录
ssh CentOS-node01
安装命令:
tar xf hadoop-2.6.5.tar.gz -C /opt/HXW //解压放在opt下以名字大写字母命名的文件夹中
cd /opt/HXW/hadoop-2.6.5 //到/opt/HXW目录下去看一下是否解压好了
实现在任意目录下启动hadoop,就要在配置文件里做些修改。
vi + /etc/profile
配置信息如下:
export JAVA_HOME=/usr/bin/java
export HADOOP_HOME=/opt/HXW/hadoop-2.6.5
export PATH=$PATH:/usr/java/jdk1.7.0_67/bin:$HADOOP_HOME/bin:$HADOOP_HOME/sbin
当在命令行上输入hd
按Tab键可以自动补全为hdfs
输入start-d
按Tab键可以自动补全为start-dfs.
就表示配置成功了
配置操作统一在下列路径下运行命令:
cd /opt/HXW/hadoop-2.6.5/etc/hadoop
注:以上路径的etc可不是根目录下的etc
vi hadoop-env.sh
vi mapred-env.sh
vi yarn-env.sh
给这三个文件里的JAVA_HOME都改成绝对路径/usr/java/jdk1.7.0_67
配置 vi core-site.xml
配置代码如下:
fs.defaultFS //配置主节点信息
hdfs://mycluster
hadoop.tmp.dir //将NN的元数据信息和DN的数据文件默认存放的临时tmp文件的路径修改掉,更安全
>/var/HXW/hadoop/pseudo
配置 vi core-site.xml
配置代码如下:
dfs.replication //Block的副本数,默认为3
1
dfs.namenode.secondary.http-address
CentOS-node01:50090 //配secondary NameNode
配置slaves文件
vi slaves
CentOS-node01
hdfs namenode -format
只能格式化一次,再次启动集群不要执行,否则clusterID变了
之前/var/HXW/hadoop/pseudo这个文件不存在,格式化后就存在了,检查一下看存在没,可以进入到这个文件里去了
start-dfs.sh
用jps
去查看都有哪些集群被启动了
在浏览器里打开CentOS-node01:50070(别用360浏览器!)能出现以下界面则有效
创建目录
hdfs dfs -mkdir -p /user/root
在 user下创建root目录,在上述浏览器界面可直接查看是否创建目录成功,如下:
上传文件
hdfs dfs -put a.txt /user/root
停止集群命令:
stop-dfs.sh
1.分发jdk到另外三台机子
在CentOS-node01上输入下列命令,进行发送:
scp jdk-7u67-linux-x64.rpm CentOS-node02:`pwd`
scp jdk-7u67-linux-x64.rpm CentOS-node03:`pwd`
scp jdk-7u67-linux-x64.rpm CentOS-node04:`pwd`
在Xshell的全部会话栏里一起ll
,看jdk是否发送成功。
注意:` 这一符号是数字1左边这个键
2.分别在 CentOS-node02、03、04上执行rpm安装命令
rpm -i jdk-7u67-linux-x64.rpm
3.在node03上cd /etc,在此目录下把profile文件分发到 CentOS-node02、03、04上。
scp profile node04:`pwd`
4.利用Xshell全部会话栏,刷新这个文件,修改才会生效 , 这一步不能忘记 !
source /etc/profile
5.利用Xshell全部会话栏,jps,看04、05、06这三台机子的jdk是否装好。
date //查看机子当前的时间。
时间不能差太大,否则集群启动后某些进程跑不起来。
*若时间不同步,怎么办?
1.yum进行时间同步器的安装
yum -y install ntp
2.执行同步命令
ntpdate time1.aliyun.com //和阿里云服务器时间同步
仔细点,真的要细心(扶额)不然有你哭的hhh
cat /etc/sysconfig/network //查看HOSTNAME是否正确
cat /etc/hosts //查看IP映射是否正确,若不正确,进行修改
cat /etc/sysconfig/selinux //查看该selinux里是否 SELINUX=disabled
service iptables status //查看防火墙是否关闭,配置过程中是要求关闭防火墙的
1. 在家目录下 ll –a
看下有无.ssh文件,如果没有就ssh loalhost
一下
2. cd .ssh
,到.ssh目录下,ll
查看一下
3. 把CentOS-node01的公钥发给其他三台机子
scp id_dsa.pub CentOS-node02:`pwd`/CentOS-node01.pub
将CentOS-node01的公钥发给CentOS-node02的pwd下 并重命名为CentOS-node01.pub
4. 在CentOS-node02的.ssh目录下看是否有CentOS-node01.pub
如果有,那就追加到authorized_keys
cat CentOS-node01.pub >> authorized_keys
5. 在CentOS-node01上ssh CentOS-node02看是否免密钥了(每次ssh一定要记得exit)
6. 同理,给其他节点发送公钥并在各个节点上把CentOS-node01的公钥追加上,并测试看ssh CentOS-node01要不要密钥
scp id_dsa.pub CentOS-node03:`pwd`/CentOS-node01.pub
cat CentOS-node01.pub >> authorized_keys
ssh CentOS-node01
exit //!!!一定要exit
scp id_dsa.pub CentOS-node04:`pwd`/CentOS-node01.pub
cat CentOS-node01.pub >> authorized_keys
ssh CentOS-node01
exit //!!!一定要exit
需实现两台NameNode ( CentOS-node01与CentOS-node02 ) 之间互相免密钥,我们已经实现CentOS-node01可免密钥登录CentOS-node02,那现需CentOS-node02上能免密钥登CentOS-node01,所以
1. 在CentOS-node02上:
ssh-keygen -t dsa -P '' -f ~/.ssh/id_dsa //生成公钥
cat ~/.ssh/id_dsa.pub >> ~/.ssh/authorized_keys
2.ssh localhost
验证一下
3. 分发到CentOS-node01上:
scp id_dsa.pub CentOS-node01:`pwd`/CentOS-node02.pub
4. 在CentOS-node01的.ssh目录下,
cat CentOS-node02.pub >> authorized_keys,
5. 在CentOS-node02上 验证一下可否免密钥登录
ssh CentOS-node01
由于CentOS-node03和CentOS-node04都是resourcemanager,所以它俩应该相互免密钥
CentOS-node03上免密钥登录CentOS-node04:
1.在CentOS-node03的.ssh目录下生成密钥
ssh-keygen -t dsa -P '' -f ./id_dsa
2.追加到自己authorized_keys
cat id_dsa.pub >> authorized_keys
3.用 ssh localhost
验证看是否需要密码,别忘了exit!
4. 将CentOS-node03的公钥分发到CentOS-node04
scp id_dsa.pub CentOS-node04:`pwd`/CentOS-node03.pub
5.在CentOS-node04的.ssh目录下,追加CentOS-node03.pub
cat CentOS-node03.pub >> authorized_keys
6. 在CentOS-node03上 ssh CentOS-node04 ,看是否免密钥
同理设置 CentOS-node04 上免密钥登录CentOS-node03,这里过程我就不赘述了,将上面03和04互相换位进行操作即可。
vi hdfs-site.xml
配置结果如下:
dfs.replication
3
dfs.nameservices
mycluster
dfs.ha.namenodes.mycluster
nn1,nn2
dfs.namenode.rpc-address.mycluster.nn1
CentOS-node01:8020
dfs.namenode.rpc-address.mycluster.nn2
CentOS-node02:8020
dfs.namenode.http-address.mycluster.nn1
CentOS-node01:50070
dfs.namenode.http-address.mycluster.nn2
CentOS-node02:50070
dfs.namenode.shared.edits.dir
qjournal://CentOS-node01:8485;CentOS-node02:8485;CentOS-node03:8485/mycluster
dfs.journalnode.edits.dir
/var/HXW/hadoop/ha/jn
dfs.client.failover.proxy.provider.mycluster
org.apache.hadoop.hdfs.server.namenode.ha.ConfiguredFailoverProxyProvider
dfs.ha.fencing.methods
sshfence
dfs.ha.fencing.ssh.private-key-files
/root/.ssh/id_dsa
dfs.ha.automatic-failover.enabled
true
vi core-site.xml
配置结果如下:
fs.defaultFS
hdfs://mycluster
ha.zookeeper.quorum
CentOS-node02:2181,CentOS-node03:2181,CentOS-node04:2181
vi slaves
CentOS-node02
CentOS-node03
CentOS-node04
为MapReduce做准备, mapreduce是在yarn运行的
把mapred-site.xml.template留个备份,并且改下名字
cp mapred-site.xml.template mapred-site.xml
vi mapred-site.xml (添加参数)
mapreduce.framework.name
yarn
vi yarn-site.xml (添加参数)
yarn.nodemanager.aux-services
mapreduce_shuffle
yarn.resourcemanager.ha.enabled
true
yarn.resourcemanager.cluster-id
cluster1
yarn.resourcemanager.ha.rm-ids
rm1,rm2
yarn.resourcemanager.hostname.rm1
CentOS-node03
yarn.resourcemanager.hostname.rm2
CentOS-node04
yarn.resourcemanager.zk-address
CentOS-node02:2181,CentOS-node03:2181,CentOS-node04:2181
scp –r HXW/ CentOS-node02:`pwd`
scp –r HXW/ CentOS-node03:`pwd`
scp –r HXW/ CentOS-node04:`pwd`
scp hdfs-site.xml core-site.xml CentOS-node02:`pwd`
scp hdfs-site.xml core-site.xml CentOS-node03:`pwd`
scp hdfs-site.xml core-site.xml CentOS-node04:`pwd`
scp mapred-site.xml yarn-site.xml CentOS-node02:`pwd`
scp mapred-site.xml yarn-site.xml CentOS-node03:`pwd`
scp mapred-site.xml yarn-site.xml CentOS-node04:`pwd`
tar xf zookeeper-3.4.6.tar.gz -C /opt/HXW
cd /opt/HXW/zookeeper-3.4.6/conf
cp zoo_sample.cfg zoo.cfg
vi zoo.cfg
改 **dataDir=/var/HXW/zk ** , 并在末尾追加
server.1=CentOS-node02:2888:3888
server.2=CentOS-node03:2888:3888
server.3=CentOS-node04:2888:3888
其中2888主从通信端口,3888是当主挂断后进行选举机制的端口
scp -r zookeeper-3.4.6/ CentOS-node03:`pwd`
scp -r zookeeper-3.4.6/ CentOS-node04:`pwd`
并用 ll /opt/HXW 检查下看分发成功没
mkdir -p /var/HXW/zk
**对CentOS-node02来说: **
echo 1 > /var/HXW/zk/myid
cat /var/HXW/zk/myid
**对CentOS-node03来说: **
echo 2 > /var/HXW/zk/myid
cat /var/HXW/zk/myid
**对CentOS-node04来说: **
echo 3 > /var/HXW/zk/myid
cat /var/HXW/zk/myid
export ZOOKEEPER_HOME=/opt/ldy/zookeeper-3.4.6
export PATH=$PATH:/usr/java/jdk1.7.0_67/bin:$HADOOP_HOME/bin:$HADOOP_HOME/sbin:$ZOOKEEPER_HOME/bin
scp /etc/profile CentOS-node03:/etc
scp /etc/profile CentOS-node04:/etc
source /etc/profie
,这步千万别忘 ! ! !验证source这句是否完成,输入zkCli.s,按Tab可以把名字补全zkCli.sh
在全部会话中输入:zkServer.sh start
把三台机子的zookeeper都启起来
接着用zkServer.sh status
查看每个zookeeper节点的状态
CentOS-node02、03、04 三台安装了zookeeper,只要是一台状态为leader,两台为follower则成功
* 注意:如果启动不起来,请把/etc/profile里的JAVA_HOME改成绝对路径。
启动journalnode是为了使两台NameNode间完成数据同步。
下一次启动hdfs集群的时候还需要用hadoop-daemon.sh start journalnode命令启动journalnode吗?
不需要,只要start-dfs.sh就可以了。这里我们启动journalnode是为了同步两个namenode之间的信息。
在01、02、03三台机子上分别把journalnode启动起来
hadoop-daemon.sh start journalnode
用 jps 检查下进程启起来了没
NameNode 要是没起来的话去 /opt/HXW/hadoop-2.6.5/logs (如下图)下查看相应的NameNode的.log文件,看哪里报错。(以后什么东西没启起来都可以到这里去查看)
( 这里需严格按步骤操作 ! !)
随意挑一台namenode上执行,另一台namenode不用执行,否则clusterID变了,找不到集群了。
hdfs namenode –format
然后,启动刚刚格式化的那台namenode
hadoop-daemon.sh start namenode
给另一台namenode同步一下数据,用以下命令
hdfs namenode -bootstrapStandby
( 这里需严格按步骤操作 ! !)
在CentOS-node01上:
hdfs zkfc -formatZK
在CentOS-node02上:
zkCli.sh //打开zookeeper客户端
启动zookeeper,全部会话中
zkServer.sh start
若zookeeper启动不成功,可能是前面一步zkfc格式化没成功,不要做太快,每一步都看清楚做仔细,回头去仔细看看报的什么错误吧
在CentOS-node01上启动集群
start-dfs.sh
如果哪个节点没起来到hadoop目录下去看那个node的日志文件log
然后全部会话jps看一下都起来些什么进程
用浏览器访问CentOS-node01:50070和CentOS-node02:50070 如下,一个为active,一个为standby
在CentOS-node01上启动yarn
start-yarn.sh
在CentOS-node03、04上分别启动resourcemanager
yarn-daemon.sh start resourcemanager
看进程全不全,全部会话jps
可在浏览器访问Cent-node03:8088,查看resourcemanager管理的内容
关闭集群命令
stop-dfs.sh //在CentOS-node01上
关闭yarn , 停止nodemanager
stop-yarn.sh //在CentOS-node01上
在CentOS-node03,CentOS-node04上
yarn-daemon.sh stop resourcemanager
在CentOS-node02、03、04上,关闭zookeeper命令
zkServer.sh stop
呼 ~ 搭建完成,去跑一个wordcount试试吧