hadoop-ha叢集搭建
一、背景
在Hadoop 2.0.0之前,HDFS叢集中只有一個namenode,如果namenode故障,那麼這個叢集將不可用,直到namenode重啟或者其他namenode接入。
有兩種方式會影響叢集的整體可用性:
1、意外的突發事件,比如物理機器crash,叢集將不可用,直到管理員重啟namenode。
2、系統維護,比如軟體升級等,需要關閉namenode,也會導致叢集暫時性的失效。
HDFS 的HA叢集特性即解決這個問題,它通過在叢集中同時執行2個namenodes,當Active namenode故障失效後,即可快速故障轉移到新的Namenode上(standby namenode),就不需要之前的secondary namenode了。
架構:
故障自動切換:zookeeper叢集 ZKFC
namenode資料最終一致性:JN叢集(journal node)
namemode的安全模式(safemode):
namenode剛啟動時,記憶體中只有檔案和檔案的塊id及副本數量,不知道塊所在的datanode。
namenode需要等待所有的datanode向他彙報自身持有的塊資訊,namenode才能在元資料中補全檔案塊資訊中的位置資訊。
只有當namenode找到99.8%的塊檔案資訊,才會退出安全模式,正常對外提供服務。
二、hadoop-ha叢集搭建
備註:和之前搭建的hadoop叢集比,增加了幾臺機器作為容錯,配置檔案上添加了修改
1.修改Linux主機名
2.修改IP
3.修改主機名和IP的對映關係 /etc/hosts
######注意######如果你們公司是租用的伺服器或是使用的雲主機(如華為用主機、阿里雲主機等)
/etc/hosts裡面要配置的是內網IP地址和主機名的對映關係
4.關閉防火牆
5.ssh免登陸
6.安裝JDK,配置環境變數等
叢集規劃:
主機名 IP 安裝的軟體 執行的程序 mini1 192.168.1.200 jdk、hadoop NameNode、DFSZKFailoverController(zkfc) mini2192.168.1.201 jdk、hadoop NameNode、DFSZKFailoverController(zkfc) mini3 192.168.1.202 jdk、hadoop ResourceManager mini4 192.168.1.203 jdk、hadoop ResourceManager mini5 192.168.1.205 jdk、hadoop、zookeeper DataNode、NodeManager、JournalNode、QuorumPeerMain mini6 192.168.1.206 jdk、hadoop、zookeeper DataNode、NodeManager、JournalNode、QuorumPeerMain mini7 192.168.1.207 jdk、hadoop、zookeeper DataNode、NodeManager、JournalNode、QuorumPeerMain
說明:
1.在hadoop2.0中通常由兩個NameNode組成,一個處於active狀態,另一個處於standby狀態。Active NameNode對外提供服務,而Standby NameNode則不對外提供服務,僅同步active namenode的狀態,以便能夠在它失敗時快速進行切換。 hadoop2.0官方提供了兩種HDFS HA的解決方案,一種是NFS,另一種是QJM。這裡我們使用簡單的QJM。在該方案中,主備NameNode之間通過一組JournalNode同步元資料資訊,一條資料只要成功寫入多數JournalNode即認為寫入成功。通常配置奇數個JournalNode 這裡還配置了一個zookeeper叢集,用於ZKFC(DFSZKFailoverController)故障轉移,當Active NameNode掛掉了,會自動切換Standby NameNode為standby狀態 2.hadoop-2.2.0中依然存在一個問題,就是ResourceManager只有一個,存在單點故障,hadoop-2.6.4解決了這個問題,有兩個ResourceManager,一個是Active,一個是Standby,狀態由zookeeper進行協調
安裝步驟:
1.安裝配置zooekeeper叢集(在hadoop05上) 1.1解壓 tar -zxvf zookeeper-3.4.5.tar.gz -C /home/hadoop/app/ 1.2修改配置 cd /home/hadoop/app/zookeeper-3.4.5/conf/ cp zoo_sample.cfg zoo.cfg vim zoo.cfg 修改:dataDir=/home/hadoop/app/zookeeper-3.4.5/tmp 在最後新增: server.1=hadoop05:2888:3888 server.2=hadoop06:2888:3888 server.3=hadoop07:2888:3888 儲存退出 然後建立一個tmp資料夾 mkdir /home/hadoop/app/zookeeper-3.4.5/tmp echo 1 > /home/hadoop/app/zookeeper-3.4.5/tmp/myid 1.3將配置好的zookeeper拷貝到其他節點(首先分別在hadoop06、hadoop07根目錄下建立一個hadoop目錄:mkdir /hadoop) scp -r /home/hadoop/app/zookeeper-3.4.5/ hadoop06:/home/hadoop/app/ scp -r /home/hadoop/app/zookeeper-3.4.5/ hadoop07:/home/hadoop/app/ 注意:修改hadoop06、hadoop07對應/hadoop/zookeeper-3.4.5/tmp/myid內容 hadoop06: echo 2 > /home/hadoop/app/zookeeper-3.4.5/tmp/myid hadoop07: echo 3 > /home/hadoop/app/zookeeper-3.4.5/tmp/myid 2.安裝配置hadoop叢集(在hadoop00上操作) 2.1解壓 tar -zxvf hadoop-2.6.4.tar.gz -C /home/hadoop/app/ 2.2配置HDFS(hadoop2.0所有的配置檔案都在$HADOOP_HOME/etc/hadoop目錄下) #將hadoop新增到環境變數中 vim /etc/profile export JAVA_HOME=/usr/java/jdk1.7.0_55 export HADOOP_HOME=/hadoop/hadoop-2.6.4 export PATH=$PATH:$JAVA_HOME/bin:$HADOOP_HOME/bin #hadoop2.0的配置檔案全部在$HADOOP_HOME/etc/hadoop下 cd /home/hadoop/app/hadoop-2.6.4/etc/hadoop 2.2.1修改hadoo-env.sh export JAVA_HOME=/home/hadoop/app/jdk1.7.0_55
2.2.2修改core-site.xml
<configuration> <!-- 指定hdfs的nameservice為ns1 --> <property> <name>fs.defaultFS</name> <value>hdfs://bi/</value> </property> <!-- 指定hadoop臨時目錄 --> <property> <name>hadoop.tmp.dir</name> <value>/home/hadoop/app/hdpdata/</value> </property> <!-- 指定zookeeper地址 --> <property> <name>ha.zookeeper.quorum</name> <value>mini5:2181,mini6:2181,mini7:2181</value> </property> </configuration>
2.2.3修改hdfs-site.xml
<configuration> <!--指定hdfs的nameservice為bi,需要和core-site.xml中的保持一致 --> <property> <name>dfs.nameservices</name> <value>bi</value> </property> <!-- bi下面有兩個NameNode,分別是nn1,nn2 --> <property> <name>dfs.ha.namenodes.bi</name> <value>nn1,nn2</value> </property> <!-- nn1的RPC通訊地址 --> <property> <name>dfs.namenode.rpc-address.bi.nn1</name> <value>mini1:9000</value> </property> <!-- nn1的http通訊地址 --> <property> <name>dfs.namenode.http-address.bi.nn1</name> <value>mini1:50070</value> </property> <!-- nn2的RPC通訊地址 --> <property> <name>dfs.namenode.rpc-address.bi.nn2</name> <value>mini2:9000</value> </property> <!-- nn2的http通訊地址 --> <property> <name>dfs.namenode.http-address.bi.nn2</name> <value>mini2:50070</value> </property> <!-- 指定NameNode的edits元資料在JournalNode上的存放位置 --> <property> <name>dfs.namenode.shared.edits.dir</name> <value>qjournal://mini5:8485;mini6:8485;mini7:8485/bi</value> </property> <!-- 指定JournalNode在本地磁碟存放資料的位置 --> <property> <name>dfs.journalnode.edits.dir</name> <value>/home/hadoop/journaldata</value> </property> <!-- 開啟NameNode失敗自動切換 --> <property> <name>dfs.ha.automatic-failover.enabled</name> <value>true</value> </property> <!-- 配置失敗自動切換實現方式 --> <property> <name>dfs.client.failover.proxy.provider.bi</name> <value>org.apache.hadoop.hdfs.server.namenode.ha.ConfiguredFailoverProxyProvider</value> </property> <!-- 配置隔離機制方法,多個機制用換行分割,即每個機制暫用一行--> <property> <name>dfs.ha.fencing.methods</name> <value> sshfence shell(/bin/true) </value> </property> <!-- 使用sshfence隔離機制時需要ssh免登陸 --> <property> <name>dfs.ha.fencing.ssh.private-key-files</name> <value>/home/hadoop/.ssh/id_rsa</value> </property> <!-- 配置sshfence隔離機制超時時間 --> <property> <name>dfs.ha.fencing.ssh.connect-timeout</name> <value>30000</value> </property> </configuration>
2.2.4修改mapred-site.xml
<configuration> <!-- 指定mr框架為yarn方式 --> <property> <name>mapreduce.framework.name</name> <value>yarn</value> </property> </configuration>
2.2.5修改yarn-site.xml
<configuration> <!-- 開啟RM高可用 --> <property> <name>yarn.resourcemanager.ha.enabled</name> <value>true</value> </property> <!-- 指定RM的cluster id --> <property> <name>yarn.resourcemanager.cluster-id</name> <value>yrc</value> </property> <!-- 指定RM的名字 --> <property> <name>yarn.resourcemanager.ha.rm-ids</name> <value>rm1,rm2</value> </property> <!-- 分別指定RM的地址 --> <property> <name>yarn.resourcemanager.hostname.rm1</name> <value>mini3</value> </property> <property> <name>yarn.resourcemanager.hostname.rm2</name> <value>mini4</value> </property> <!-- 指定zk叢集地址 --> <property> <name>yarn.resourcemanager.zk-address</name> <value>mini5:2181,mini6:2181,mini7:2181</value> </property> <property> <name>yarn.nodemanager.aux-services</name> <value>mapreduce_shuffle</value> </property> </configuration>
2.2.6 修改slaves(slaves是指定子節點的位置,因為要在hadoop01上啟動HDFS、在hadoop03啟動yarn,所以hadoop01上的slaves檔案指定的是datanode的位置,hadoop03上的slaves檔案指定的是nodemanager的位置)
mini5 mini6 mini7
2.2.7配置免密碼登陸
#首先要配置hadoop00到hadoop01、hadoop02、hadoop03、hadoop04、hadoop05、hadoop06、hadoop07的免密碼登陸 #在hadoop01上生產一對鑰匙 ssh-keygen -t rsa #將公鑰拷貝到其他節點,包括自己 ssh-coyp-id hadoop00 ssh-coyp-id hadoop01 ssh-coyp-id hadoop02 ssh-coyp-id hadoop03 ssh-coyp-id hadoop04 ssh-coyp-id hadoop05 ssh-coyp-id hadoop06 ssh-coyp-id hadoop07 #配置hadoop02到hadoop04、hadoop05、hadoop06、hadoop07的免密碼登陸 #在hadoop02上生產一對鑰匙 ssh-keygen -t rsa #將公鑰拷貝到其他節點 ssh-coyp-id hadoop03 ssh-coyp-id hadoop04 ssh-coyp-id hadoop05 ssh-coyp-id hadoop06 ssh-coyp-id hadoop07 #注意:兩個namenode之間要配置ssh免密碼登陸,別忘了配置hadoop01到hadoop00的免登陸 在hadoop01上生產一對鑰匙 ssh-keygen -t rsa ssh-coyp-id -i hadoop00
2.4將配置好的hadoop拷貝到其他節點
scp -r /hadoop/ hadoop02:/ scp -r /hadoop/ hadoop03:/ scp -r /hadoop/hadoop-2.6.4/ hadoop@hadoop04:/hadoop/ scp -r /hadoop/hadoop-2.6.4/ hadoop@hadoop05:/hadoop/ scp -r /hadoop/hadoop-2.6.4/ hadoop@hadoop06:/hadoop/ scp -r /hadoop/hadoop-2.6.4/ hadoop@hadoop07:/hadoop/
###注意:嚴格按照下面的步驟
2.5啟動zookeeper叢集(分別在mini5、mini6、mini7上啟動zk)
cd /hadoop/zookeeper-3.4.5/bin/ ./zkServer.sh start #檢視狀態:一個leader,兩個follower ./zkServer.sh status
2.6啟動journalnode(分別在在mini5、mini6、mini7上執行)
cd /hadoop/hadoop-2.6.4 sbin/hadoop-daemon.sh start journalnode #執行jps命令檢驗,hadoop05、hadoop06、hadoop07上多了JournalNode程序
2.7格式化HDFS
#在mini1上執行命令: hdfs namenode -format #格式化後會在根據core-site.xml中的hadoop.tmp.dir配置生成個檔案,這裡我配置的是/hadoop/hadoop-2.6.4/tmp,然後將/hadoop/hadoop-2.6.4/tmp拷貝到hadoop02的/hadoop/hadoop-2.6.4/下。 scp -r tmp/ hadoop02:/home/hadoop/app/hadoop-2.6.4/ ##也可以這樣,建議hdfs namenode -bootstrapStandby
2.8格式化ZKFC(在mini1上執行一次即可)
hdfs zkfc -formatZK
2.9啟動HDFS(在mini1上執行)\
sbin/start-dfs.sh
2.10啟動YARN(#####注意#####:是在hadoop02上執行start-yarn.sh,把namenode和resourcemanager分開是因為效能問題,因為他們都要佔用大量資源,所以把他們分開了,他們分開了就要分別在不同的機器上啟動)
sbin/start-yarn.sh
到此,hadoop-2.6.4配置完畢,可以統計瀏覽器訪問:
http://hadoop00:50070 NameNode 'hadoop01:9000' (active) http://hadoop01:50070 NameNode 'hadoop02:9000' (standby)
驗證HDFS HA
首先向hdfs上傳一個檔案 hadoop fs -put /etc/profile /profile hadoop fs -ls / 然後再kill掉active的NameNode kill -9 <pid of NN> 通過瀏覽器訪問:http://192.168.1.202:50070 NameNode 'hadoop02:9000' (active) 這個時候hadoop02上的NameNode變成了active 在執行命令: hadoop fs -ls / -rw-r--r-- 3 root supergroup 1926 2014-02-06 15:36 /profile 剛才上傳的檔案依然存在!!! 手動啟動那個掛掉的NameNode sbin/hadoop-daemon.sh start namenode 通過瀏覽器訪問:http://192.168.1.201:50070 NameNode 'hadoop01:9000' (standby)
驗證YARN:
執行一下hadoop提供的demo中的WordCount程式: hadoop jar share/hadoop/mapreduce/hadoop-mapreduce-examples-2.4.1.jar wordcount /profile /out
OK,大功告成!!!
更多java、大資料學習面試資料,請掃碼關注我的公眾號:
專注於大資料和java開發,學習交流可以關注我的公眾號:javaydsj