自己的主機上的Hadoop版本是2.7.6,是測試用的偽分布式Hadoop,在前段時間部署了Hive on Spark,但由於沒有做好功課,導致了Hive無法正常啟動,原因在於Hive 3.x版本不適配Hadoop 2.x版本。之前我在學校服務器上部署的Hadoop版本是3.1.2,現打算將自己的從2.7.6升級到3.1.2版本,同時也當作練練手並記錄以便以后參考。這是一個大版本跨度的升級操作,所以先參考Hadoop權威指南上的方案以及官方文檔,然后擬定了升級和回滾方案。
根據官方文檔所說:
”For non-HA clusters, it is impossible to upgrade HDFS without downtime since it requires restarting the namenodes. However, datanodes can still be upgraded in a rolling manner.“
也就是說對於非HA群集,由於需要重新啟動名稱節點,因此無法在沒有停機的情況下升級HDFS。但是,仍可以回滾方式升級datanode。
注意:僅從Hadoop-2.4.0開始支持滾動升級。
Hadoop升級最主要是HDFS的升級,HDFS的升級是否成功,才是升級的關鍵,如果升級出現數據丟失,則其他升級就變得毫無意義。
解決方法:
- 備份HDFS的NameNode元數據,升級后,對比升級前后的文件信息。
- 單台升級DataNode,觀察升級前后的Block數(有較小浮動范圍,v2與v3的計數方式不一樣)。
第一階段 停機以及備份NameNode目錄
通過命令stop-yarn.sh和stop-dfs.sh關閉HDFS集群:
# stop-yarn.sh # stop-dfs.sh
然后備份NameNode目錄到NFS或者其他文件系統中,如果不記得NameNode目錄存儲的地址可以通過查看hdfs-site.xml文件的:
# vim $HADOOP_HOME/etc/hadoop/hdfs-site.xml
第二階段 在集群上安裝新版本的Hadoop
下載Hadoop 3.1.2后解壓,最好移除PATH環境變量下的Hadoop腳本,這樣的話,就不會混淆針對不同版本的腳本。將HADOOP_HOME指向新的Hadoop:
接下來將${HADOOP_HOME}/etc/hadoop/hdfs-site.xml中的dfs.namenode.name.dir和dfs.datanode.data.dir屬性的值分別指向Hadoop 2.7.6的hdfs-site.xml的dfs.namenode.name.dir和dfs.datanode.data.dir屬性的值。
第三階段 准備滾動升級
在hdfs-site.xml增加屬性:
<property> <name>dfs.namenode.duringRollingUpgrade.enable</name> <value>true</value> </property>
先啟動舊版本的Hadoop:
# /usr/local/hadoop/sbin/start-dfs.sh
進入安全模式:
# hdfs dfsadmin -safemode enter
准備滾動升級:
1. 運行“hdfs dfsadmin -rollingUpgrade prepare”以創建用於回滾的fsimage。
2. 運行"hdfs dfsadmin -rollingUpgrade query"以檢查回滾映像的狀態。等待並重新運行該命令,直到顯示“繼續滾動升級”消息。
第四階段 升級NN與SNN
1. 關閉SNN:
# /usr/local/hadoop/sbin/hadoop-daemon.sh stop secondarynamenode
2. 關閉NameNode和DataNode:
# /usr/local/hadoop/sbin/hadoop-daemon.sh stop namenode
# /usr/local/hadoop/sbin/hadoop-daemon.sh stop datanode
3. 在新版本的Hadoop使用“-rollingUpgrade started”選項啟動NN:
進入新版本的Hadoop目錄,然后以升級的方式啟動NameNode:
# $HADOOP_HOME/bin/hdfs --daemon start namenode -rollingUpgrade started
升級hdfs花費的時間不長,升級丟失數據的風險幾乎沒有。
接下來升級並重啟SNN:
# $HADOOP_HOME/bin/hdfs --daemon start secondarynamenode
第五階段 升級DN
由於我升級的Hadoop是偽分布式的,NameNode和DataNode是在同一節點上,按集群升級分類來說,屬於非HA集群升級。在這里,升級DataNode是比較簡單的,在新版本的Hadoop上重新啟動DataNode即可,等待一會,DataNode自動升級成功。
# $HADOOP_HOME/bin/hdfs --daemon start datanode
無論Hadoop是非HA還是HA,且是完全分布式的話,DataNode節點較多的情況下,可以參考官方文檔的思路(寫腳本實現):
- 選擇一小部分數據節點(例如特定機架下的所有數據節點)
- 運行“hdfs dfsadmin -shutdownDatanode <DATANODE_HOST:IPC_PORT> upgrade”以關閉其中一個選定的數據節點。
- 運行"hdfs dfsadmin -getDatanodeInfo <DATANODE_HOST:IPC_PORT>"以檢查並等待datanode關閉。
- 升級並重新啟動datanode
- 對子集中所有選定的數據節點並行執行上述步驟。
2. 重復上述步驟,直到升級群集中的所有數據節點。
等待升級完成后,可以查看Web頁面,NameNode和DataNode版本已經升級為3.1.2版本:
此時可以已完成滾動升級:
# $HADOOP_HOME/bin/hdfs dfsadmin -rollingUpgrade finalize
如果升級失敗,可以隨時回滾,回滾,數據會回滾到升級前那一刻的數據,升級后的數據修改,全部失效,回滾啟動步驟如下:
# /usr/local/hadoop/bin/hadoop-daemon.sh start namenode –rollback # /usr/local/hadoop/bin/hadoop-daemon.sh start datanode –rollback
遇到的問題:
參考網址: https://stackoverflow.com/questions/21369102/hadoop-command-not-found
解決方法:查找配置環境變量的文件,/etc/profile、~/.bashrc、hadoop-env.sh,發現在~/.bashrc文件中配置了HADOOP_HOME,用了舊版本的路徑,刪除或者更新為新的環境變量即可。
參考資料: 《Hadoop權威指南(第四版)》