一、HDFS體系結構
HDFS支持主從結構,主節點稱為 NameNode ,是因為主節點上運行的有NameNode進程,NameNode支持多個。從節點稱為 DataNode ,是因為從節點上面運行的有DataNode進程,DataNode支持多個。HDFS中還包含一個 SecondaryNameNode 進程,這個進程從字面意思上看像是第二個NameNode的意思,其實不是。
在這大家可以這樣理解:
公司BOSS:NameNode
秘書:SecondaryNameNode
員工:DataNode
接着看一下這張圖,這就是HDFS的體系結構,這里面的TCP、RPC、HTTP表示是不同的網絡通信方式,通過這張圖是想加深大家對HDFS體系結構的理解。
二、NameNode介紹
首先是NameNode,NameNode是整個文件系統的管理節點
它主要維護着整個文件系統的文件目錄樹,文件/目錄的信息 和 每個文件對應的數據塊列表,並且還負責接收用戶的操作請求
-
目錄樹:表示目錄之間的層級關系,就是我們在hdfs上執行ls命令可以看到的那個目錄結構信息。
-
文件/目錄的信息:表示文件/目錄的的一些基本信息,所有者 屬組 修改時間 文件大小等信息。
-
每個文件對應的數據塊列表:如果一個文件太大,那么在集群中存儲的時候會對文件進行切割,這個時候就類似於會給文件分成一塊一塊的,存儲到不同機器上面。所以HDFS還要記錄一下一個文件到底被分了多少塊,每一塊都在什么地方存儲
- 接收用戶的操作請求:其實我們在命令行使用hdfs操作的時候,是需要先和namenode通信 才能開始去操作數據的。
為什么呢?因為文件信息都在namenode上面存儲着的,namenode是非常重要的,它的這些信息最終是會存儲到文件上的,那接下來我們來看一下NameNode中包含的那些文件。
NameNode主要包括以下文件:
這些文件所在的路徑是由hdfs-default.xml的dfs.namenode.name.dir屬性控制的
hdfs-default.xml文件在哪呢?
我使用的是HDP,它在/usr/hdp/2.6.5.0-292/hadoop-hdfs/hadoop-hdfs-2.7.3.2.6.5.0-292.jar,這個文件中包含了HDFS相關的所有默認參數,咱們在配置集群的時候會修改一個hdfs-site.xml文件(位置/usr/hdp/2.6.5.0-292/hadoop/conf),hdfs-site.xml文件屬於hdfs-default.xml的一個擴展,它可以覆蓋掉hdfs-default.xml中同名的參數。
那我們來看一下這個文件中的dfs.namenode.name.dir屬性
進入到/data1/hadoop/hdfs/namenode目錄下
發現這個下面會有一個current 目錄,表示當前的意思,還有一個in_use.lock 這個只是一個普通文件,但是它其實有特殊的含義,你看他的文件名后綴值lock 表示是鎖的意思,文件名是in_use 表示這個文件現在正在使用,不允許你再啟動namenode。
當我們啟動namonde的時候 會判斷這個目錄下是否有in_use.lock 這個相當於一把鎖,如果沒有的話,才可以啟動成功,啟動成功之后就會加一把鎖, 停止的時候會把這個鎖去掉
里面有edits文件和fsimage文件
1、fsimage文件
fsimage文件有兩個文件名相同的,有一個后綴是md5 md5是一種加密算法,這個其實主要是為了做md5校驗的,為了保證文件傳輸的過程中不出問題,相同內容的md5是一樣的,所以后期如果我把這個fsimage和對應的fsimage.md5發給你 然后你根據md5對fsimage的內容進行加密,獲取一個值 和fsimage.md5中的內容進行比較,如果一樣,說明你接收到的文件就是完整的。
我們在網站下載一些軟件的時候 也會有一些md5文件,方便驗證下載的文件是否完整。在這里可以把fsimage 拆開 fs 是文件系統 filesystem image是鏡像,說明是文件系統鏡像,就是給文件照了一個像,把文件的當前信息記錄下來。我們可以看一下這個文件,這個文件需要使用特殊的命令進行查看
-i 輸入文件 -o 輸出文件
sudo -u hdfs hdfs oiv -p XML -i fsimage_0000000000186514797 -o fsimage56.xml
fsimage56.xml文件如下,里面最外層是一個fsimage標簽,看里面的inode標簽,這個inode表示是hdfs中的每一個目錄或者文件信息:
- id:唯一編號
- type:文件類型
- name:文件名稱
- replication:文件的副本數量
- mtime:修改時間
- atime:訪問時間
- preferredBlockSize:推薦每一個數據塊的大小
- permission:權限信息
- blocks:包含多少數據塊【文件被切成數據塊】
- block:內部的id表示是塊id,genstamp是一個唯一編號,numBytes表示當前數據塊的實際大小,storagePolicyId表示是數據的存儲策略
這個文件中其實就維護了整個文件系統的文件目錄樹,文件/目錄的元信息和每個文件對應的數據塊列表,所以說fsimage中存放了hdfs最核心的數據。
2、edits文件
當我們上傳一個文件的時候,上傳一個10G的文件,假設傳到9G的時候上傳失敗了,這個時候就需要重新傳,那hdfs怎么知道這個文件失敗了呢?這個是在edits文件中記錄的。
當我們上傳大文件的時候,一個大文件會分為多個block,那么edits文件中就會記錄這些block的上傳狀態,只有當全部block都上傳成功了以后,這個時候edits中才會記錄這個文件上傳成功了,那么我們執行hdfs dfs -ls 的時候就能查到這個文件了,所以當我們在hdfs中執行ls命令的時候,其實會查詢fsimage和edits中的內容。
為什么會有這兩個文件呢?首先,我們固化的一些文件內容是存儲在fsimage文件中,當前正在上傳的文件信息是存儲在edits文件中。 這個時候我們來查看一下這個edits文件的內容,挑一個edits文件內容多一些的文件
hdfs oev -i edits_0000000000000000057-0000000000000000065 -o edits.xml
分析生成的edits.xml文件,這個地方注意,可能有的edits文件生成的edits.xml為空,需要多試幾個。這個edits.xml中可以大致看一下,里面有很多record。每一個record代表不同的操作,例如 OP_ADD,OP_CLOSE 等等,具體挑一個實例進行分析。
- OP_ADD:執行上傳操作
- OP_ALLOCATE_BLOCK_ID:申請block塊id
- OP_SET_GENSTAMP_V2:設置GENSTAMP
- OP_ADD_BLOCK:添加block塊
- OP_CLOSE:關閉上傳操作
<RECORD> <OPCODE>OP_ADD</OPCODE> <DATA> <TXID>58</TXID> <LENGTH>0</LENGTH> <INODEID>16396</INODEID> <PATH>/user.txt</PATH> <REPLICATION>3</REPLICATION> <MTIME>1586349095694</MTIME> <ATIME>1586349095694</ATIME> <BLOCKSIZE>134217728</BLOCKSIZE> <CLIENT_NAME>DFSClient_NONMAPREDUCE_-1768454371_1</CLIENT_NAME> <CLIENT_MACHINE>192.168.182.1</CLIENT_MACHINE> <OVERWRITE>true</OVERWRITE> <PERMISSION_STATUS> <USERNAME>yehua</USERNAME> <GROUPNAME>supergroup</GROUPNAME> <MODE>420</MODE> </PERMISSION_STATUS> <ERASURE_CODING_POLICY_ID>0</ERASURE_CODING_POLICY_ID> <RPC_CLIENTID>1722b83a-2dc7-4c46-baa9-9fa956b755cd</RPC_CLIENTID> <RPC_CALLID>0</RPC_CALLID> </DATA> </RECORD> <RECORD> <OPCODE>OP_ALLOCATE_BLOCK_ID</OPCODE> <DATA> <TXID>59</TXID> <BLOCK_ID>1073741830</BLOCK_ID> </DATA> </RECORD> <RECORD> <OPCODE>OP_SET_GENSTAMP_V2</OPCODE> <DATA> <TXID>60</TXID> <GENSTAMPV2>1006</GENSTAMPV2> </DATA> </RECORD> <RECORD> <OPCODE>OP_ADD_BLOCK</OPCODE> <DATA> <TXID>61</TXID> <PATH>/user.txt</PATH> <BLOCK> <BLOCK_ID>1073741830</BLOCK_ID> <NUM_BYTES>0</NUM_BYTES> <GENSTAMP>1006</GENSTAMP> </BLOCK> <RPC_CLIENTID/> <RPC_CALLID>-2</RPC_CALLID> </DATA> </RECORD> <RECORD> <OPCODE>OP_CLOSE</OPCODE> <DATA> <TXID>62</TXID> <LENGTH>0</LENGTH> <INODEID>0</INODEID> <PATH>/user.txt</PATH> <REPLICATION>3</REPLICATION> <MTIME>1586349096480</MTIME> <ATIME>1586349095694</ATIME> <BLOCKSIZE>134217728</BLOCKSIZE> <CLIENT_NAME/> <CLIENT_MACHINE/> <OVERWRITE>false</OVERWRITE> <BLOCK> <BLOCK_ID>1073741830</BLOCK_ID> <NUM_BYTES>17</NUM_BYTES> <GENSTAMP>1006</GENSTAMP> </BLOCK> <PERMISSION_STATUS> <USERNAME>yehua</USERNAME> <GROUPNAME>supergroup</GROUPNAME> <MODE>420</MODE> </PERMISSION_STATUS> </DATA> </RECORD>
這里面的每一個record都有一個事務id,txid,事務id是連續的,其實一個put操作會在edits文件中產生很多的record,對應的就是很多步驟,這些步驟對我們是屏蔽的。
注意了,根據我們剛才的分析,我們所有對hdfs的增刪改操作都會在edits文件中留下信息,那么fsimage文件中的內容是從哪來的?其實是這樣的,edits文件會定期合並到fsimage文件中。
有同學可能有疑問了,edits文件和fsimage文件中的內容是不一樣的,這怎么能是合並出來的呢?
注意,這個其實是框架去做的,在合並的時候會對edits中的內容進行轉換,生成新的內容,其實edits中保存的內容是不是太細了,單單一個上傳操作就分為了好幾步,其實上傳成功之后,我們只需要保存文件具體存儲的block信息就行了把,所以在合並的時候其實是對edits中的內容進行了精簡。
他們具體合並的代碼我們不用太過關注,但是我們要知道是那個進程去做的這個事情,其實就是我們之前提到的secondarynamenode。這個進程就是負責定期的把edits中的內容合並到fsimage中。他只做一件事,這是一個單獨的進程,在實際工作中部署的時候,也需要部署到一個單獨的節點上面。
3、seentxid文件
current目錄中還有一個seentxid文件,HDFS format之后是0,它代表的是namenode里面的edits*文件的尾數,namenode重啟的時候,會按照seen_txid的數字,順序從頭跑edits_0000001~到seen_txid的數字。如果根據對應的seen_txid無法加載到對應的文件,NameNode進程將不會完成啟動以保護數據一致性。
4、VERSION文件
這里面顯示的集群的一些信息、當重新對hdfs格式化之后,這里面的信息會變化。
總結:
(1)fsimage: 元數據鏡像文件,存儲某一時刻NameNode內存中的元數據信息,就類似是定時做了一個快照操作。【這里的元數據信息是指文件目錄樹、文件/目錄的信息、每個文件對應的數據塊列表】
(2)edits: 操作日志文件【事務文件】,這里面會實時記錄用戶的所有操作
(3)seentxid: 是存放transactionId的文件,format之后是0,它代表的是namenode里面的edits*文件的尾數,namenode重啟的時候,會按照seen_txid的數字,順序從頭跑edits_0000001~到seen_txid的數字。如果根據對應的seen_txid無法加載到對應的文件,NameNode進程將不會完成啟動以保護數據一致性。
(4)VERSION:保存了集群的版本信息
NameNode中的元數據是存儲在哪里?首先,我們做個假設,如果存儲在NameNode節點的磁盤中,因為經常需要進行隨機訪問,還有響應客戶請求,必然是效率過低。因此,元數據需要存放在內存中。但如果只存在內存中,一旦斷電,元數據丟失,整個集群就無法工作了。因此產生在磁盤中備份元數據的FsImage。
這樣又會帶來新的問題,當在內存中的元數據更新時,如果同時更新FsImage,就會導致效率過低,但如果不更新,就會發生一致性問題,一旦NameNode節點斷電,就會產生數據丟失。因此,引入Edits文件(只進行追加操作,效率很高)。每當元數據有更新或者添加元數據時,修改內存中的元數據並追加到Edits中。這樣,一旦NameNode節點斷電,可以通過FsImage和Edits的合並,合成元數據。
但是,如果長時間添加數據到Edits中,會導致該文件數據過大,效率降低,而且一旦斷電,恢復元數據需要的時間過長。因此,需要定期進行FsImage和Edits的合並,如果這個操作由NameNode節點完成,又會效率過低。因此,引入一個新的節點SecondaryNamenode,專門用於FsImage和Edits的合並。
所以NameNode的工作機制是這樣的:
第一階段:NameNode啟動
(1)第一次啟動NameNode格式化后,創建Fsimage和Edits文件。如果不是第一次啟動,直接加載編輯日志和鏡像文件到內存。
(2)客戶端對元數據進行增刪改的請求。
(3)NameNode記錄操作日志,更新滾動日志。
(4)NameNode在內存中對元數據進行增刪改。
第二階段:Secondary NameNode工作
(1)Secondary NameNode詢問NameNode是否需要CheckPoint。直接帶回NameNode是否檢查結果。
(2)Secondary NameNode請求執行CheckPoint。
(3)NameNode滾動正在寫的Edits日志。
(4)將滾動前的編輯日志和鏡像文件拷貝到Secondary NameNode。
(5)Secondary NameNode加載編輯日志和鏡像文件到內存,並合並。
(6)生成新的鏡像文件fsimage.chkpoint。
(7)拷貝fsimage.chkpoint到NameNode。
(8)NameNode將fsimage.chkpoint重新命名成fsimage。
三、SecondaryNameNode介紹
剛才在分析edits日志文件的時候我們已經針對SecondaryNameNode做了介紹,在這里再做一個總結,以示重視。
SecondaryNameNode主要負責定期的把edits文件中的內容合並到fsimage中,這個合並操作稱為checkpoint,在合並的時候會對edits中的內容進行轉換,生成新的內容保存到fsimage文件中。
注意:在NameNode的HA架構中沒有SecondaryNameNode進程,文件合並操作會由standby NameNode負責實現。
所以在Hadoop集群中,SecondaryNameNode進程並不是必須的。
下圖是工作中SecondaryNameNode掛了,在重啟SecondaryNameNode節點時Ambari的提示,提示內容:開啟namenode節點安全模式,創建一個checkpoint。
四、DateNode介紹
DataNode是提供真實文件數據的存儲服務。針對datanode主要掌握兩個概念,一個是block,一個是replication。
首先是block,HDFS會按照固定的大小,順序對文件進行划分並編號,划分好的每一個塊稱一個Block,HDFS默認Block大小是 128MB。
Blokc塊是HDFS讀寫數據的基本單位,不管你的文件是文本文件 還是視頻 或者音頻文件,針對hdfs而言都是字節。
以user.txt文件為例,他的block信息可以在fsimage文件中看到,也可以在hdfs webui上面看到, 里面有block的id信息,並且也會顯示這個數據在哪個節點上面
這里顯示在bigdata02和bigdata03上面都有,那我們過去看一下,datanode中數據的具體存儲位置是由dfs.datanode.data.dir來控制的,通過查詢hdfs-default.xml可以知道
然后進入current目錄,繼續一路往下走
[root@bigdata02 data]# cd current/ [root@bigdata02 current]# ll total 4 drwx------. 4 root root 54 Apr 8 20:30 BP-1517789416-192.168.182.100-1586268855170 -rw-r--r--. 1 root root 229 Apr 8 20:30 VERSION [root@bigdata02 current]# cd BP-1517789416-192.168.182.100-1586268855170/ [root@bigdata02 BP-1517789416-192.168.182.100-1586268855170]# ll total 4 drwxr-xr-x. 4 root root 64 Apr 8 20:25 current -rw-r--r--. 1 root root 166 Apr 7 22:21 scanner.cursor drwxr-xr-x. 2 root root 6 Apr 8 20:30 tmp [root@bigdata02 BP-1517789416-192.168.182.100-1586268855170]# cd current/ [root@bigdata02 current]# ll total 8 -rw-r--r--. 1 root root 20 Apr 8 20:25 dfsUsed drwxr-xr-x. 3 root root 21 Apr 8 15:34 finalized drwxr-xr-x. 2 root root 6 Apr 8 22:13 rbw -rw-r--r--. 1 root root 146 Apr 8 20:30 VERSION [root@bigdata02 current]# cd finalized/ [root@bigdata02 finalized]# ll total 0 drwxr-xr-x. 3 root root 21 Apr 8 15:34 subdir0 [root@bigdata02 finalized]# cd subdir0/ [root@bigdata02 subdir0]# ll total 4 drwxr-xr-x. 2 root root 4096 Apr 8 22:13 subdir0 [root@bigdata02 subdir0]# cd subdir0/ [root@bigdata02 subdir0]# ll total 340220 -rw-r--r--. 1 root root 22125 Apr 8 15:55 blk_1073741828 -rw-r--r--. 1 root root 183 Apr 8 15:55 blk_1073741828_1004.meta -rw-r--r--. 1 root root 1361 Apr 8 15:55 blk_1073741829 -rw-r--r--. 1 root root 19 Apr 8 15:55 blk_1073741829_1005.meta -rw-r--r--. 1 root root 17 Apr 8 20:31 blk_1073741830 -rw-r--r--. 1 root root 11 Apr 8 20:31 blk_1073741830_1006.meta -rw-r--r--. 1 root root 134217728 Apr 8 22:13 blk_1073741831 -rw-r--r--. 1 root root 1048583 Apr 8 22:13 blk_1073741831_1007.meta -rw-r--r--. 1 root root 134217728 Apr 8 22:13 blk_1073741832 -rw-r--r--. 1 root root 1048583 Apr 8 22:13 blk_1073741832_1008.meta -rw-r--r--. 1 root root 77190019 Apr 8 22:13 blk_1073741833 -rw-r--r--. 1 root root 603055 Apr 8 22:13 blk_1073741833_1009.meta
這里面就有很多的block塊了,注意: 這里面的.meta文件也是做校驗用的。
根據前面看到的blockid信息到這對應的找到文件,可以直接查看,發現文件內容就是我們之前上傳上去的內容。
[root@bigdata02 subdir0]# cat blk_1073741830
jack
tom
jessic
注意:這個block中的內容可能只是文件的一部分,如果你的文件較大的話,就會分為多個block存儲,默認 hadoop3中一個block的大小為128M。根據字節進行截取,截取到128M就是一個block。如果文件大小沒有默認的block塊大,那最終就只有一個block。
HDFS中,如果一個文件小於一個數據塊的大小,那么並不會占用整個數據塊的存儲空間
size是表示我們上傳文件的實際大小,blocksize是指文件的最大塊大小。
假設我們上傳了兩個10M的文件 又上傳了一個200M的文件
問1:會產生多少個block塊? 4個
問2:在hdfs中會顯示幾個文件?3個
下面看一下副本,副本表示數據有多少個備份
我們現在的集群有兩個從節點,所以最多可以有2個備份,這個是在hdfs-site.xml中進行配置的,dfs.replication 默認這個參數的配置是3。表示會有3個副本。副本只有一個作用就是保證數據安全。
DataNode工作機制
(1)一個數據塊在DataNode上以文件形式存儲在磁盤上,包括兩個文件,一個是數據本身,一個是元數據包括數據塊的長度,塊數據的校驗和,以及時間戳。
(2)DataNode啟動后向NameNode注冊,通過后,周期性(1小時)地向NameNode上報所有的塊信息。
(3)心跳是每3秒一次,心跳返回結果帶有NameNode給該DataNode的命令如復制塊數據到另一台機器,或刪除某個數據塊。如果超過10分鍾沒有收到某個DataNode的心跳,則認為該節點不可用。
(4)集群運行中可以安全加入和退出一些機器。
DataNode數據損壞
(1)當DataNode讀取Block的時候,它會計算CheckSum。
(2)如果計算后的CheckSum,與Block創建時值不一樣,說明Block已經損壞。
(3)Client讀取其他DataNode上的Block。
(4)DataNode在其文件創建后周期驗證CheckSum。
五、NameNode總結
注意:block塊存放在哪些datanode上,只有datanode自己知道,當集群啟動的時候,datanode會掃描自己節點上面的所有block塊信息,然后把節點和這個節點上的所有block塊信息告訴給namenode。這個關系是每次重啟集群都會動態加載的【這個其實就是集群為什么數據越多,啟動越慢的原因】
咱們之前說的fsimage(edits)文件中保存的有文件和block塊之間的信息。
這里說的是block塊和節點之間的關系,這兩塊關聯在一起之后,就可以根據文件找到對應的block塊,再根據block塊找到對應的datanode節點,這樣就真正找到了數據。
所以說 其實namenode中不僅維護了文件和block塊的信息 還維護了block塊和所在的datanode節點的信息。
可以理解為namenode維護了兩份關系:
第一份關系:file 與block list的關系,對應的關系信息存儲在fsimage和edits文件中,當NameNode啟動的時候會把文件中的元數據信息加載到內存中
第二份關系:datanode與block的關系,對應的關系主要在集群啟動的時候保存在內存中,當DataNode啟動時會把當前節點上的Block信息和節點信息上報給NameNode
注意了,剛才我們說了NameNode啟動的時候會把文件中的元數據信息加載到內存中,然后每一個文件的元數據信息會占用150字節的內存空間,這個是恆定的,和文件大小沒有關系,咱們前面在介紹HDFS的時候說過,HDFS不適合存儲小文件,其實主要原因就在這里,不管是大文件還是小文件,一個文件的元數據信息在NameNode中都會占用150字節,NameNode節點的內存是有限的,所以它的存儲能力也是有限的,如果我們存儲了一堆都是幾KB的小文件,最后發現NameNode的內存占滿了,確實存儲了很多文件,但是文件的總體大小卻很小,這樣就失去了HDFS存在的價值
最后,在datanode的數據目錄下面的current目錄中也有一個VERSION文件。這個VERSION和namenode的VERSION文件是有一些相似之處的,我們來具體對比一下兩個文件的內容。
namenode的VERSION文件
[root@bigdata01 current]# cat VERSION #Wed Apr 08 20:30:00 CST 2020 namespaceID=498554338 clusterID=CID-cc0792dd-a861-4a3f-9151-b0695e4c7e70 cTime=1586268855170 storageType=NAME_NODE blockpoolID=BP-1517789416-192.168.182.100-1586268855170 layoutVersion=-65
datanode的VERSION文件
[root@bigdata02 current]# cat VERSION #Wed Apr 08 20:30:04 CST 2020 storageID=DS-0e86cd27-4961-4526-bacb-3b692a90b1b0 clusterID=CID-cc0792dd-a861-4a3f-9151-b0695e4c7e70 cTime=0 datanodeUuid=0b09f3d7-442d-4e28-b3cc-2edb0991bae3 storageType=DATA_NODE layoutVersion=-57
我們前面說了namenode不要隨便格式化,因為格式化了以后VERSION里面的clusterID會變,但是datanode的VERSION中的clusterID並沒有變,所以就對應不上了。如果確實要重新格式化的話需要把/data/hadoop_repo數據目錄下的內容都清空,全部都重新生成是可以的。
六、HDFS的回收站
我們windows系統里面有一個回收站,當想恢復刪除的文件的話就可以到這里面進行恢復,HDFS也有回收站。
HDFS會為每一個用戶創建一個回收站目錄:/user/用戶名/.Trash/,每一個被用戶在Shell命令行刪除的文件/目錄,會進入到對應的回收站目錄中,在回收站中的數據都有一個生存周期,也就是當回收站中的文件/目錄在一段時間之內沒有被用戶恢復的話,HDFS就會自動的把這個文件/目錄徹底刪除,之后,用戶就永遠也找不回這個文件/目錄了。
默認情況下hdfs的回收站是沒有開啟的,需要通過一個配置來開啟,在core-site.xml中添加如下配置,value的單位是分鍾,1440分鍾表示是一天的生存周期
<property>
<name>fs.trash.interval</name>
<value>1440</value>
</property>
在修改配置信息之前先驗證一下刪除操作,顯示的是直接刪除掉了。
[root@bigdata01 hadoop-3.2.0]# hdfs dfs -rm -r /NOTICE.txt Deleted /NOTICE.txt
修改回收站配置,先在bigdata01上操作,然后再同步到其它兩個節點,先停止集群
[root@bigdata01 hadoop-3.2.0]# sbin/stop-all.sh [root@bigdata01 hadoop-3.2.0]# vi etc/hadoop/core-site.xml <configuration> <property> <name>fs.defaultFS</name> <value>hdfs://bigdata01:9000</value> </property> <property> <name>hadoop.tmp.dir</name> <value>/data/hadoop_repo</value> </property> <property> <name>fs.trash.interval</name> <value>1440</value> </property> </configuration> [root@bigdata01 hadoop-3.2.0]# scp -rq etc/hadoop/core-site.xml bigdata02:/data/soft/hadoop-3.2.0/etc/hadoop/ [root@bigdata01 hadoop-3.2.0]# scp -rq etc/hadoop/core-site.xml bigdata03:/data/soft/hadoop-3.2.0/etc/hadoop/
啟動集群,再執行刪除操作
[root@bigdata01 hadoop-3.2.0]# sbin/start-all.sh [root@bigdata01 hadoop-3.2.0]# hdfs dfs -rm -r /README.txt 2020-04-09 11:43:47,664 INFO fs.TrashPolicyDefault: Moved: 'hdfs://bigdata01:9000/README.txt' to trash at: hdfs://bigdata01:9000/user/root/.Trash/Current/README.txt
此時看到提示信息說把刪除的文件移到到了指定目錄中,其實就是移動到了當前用戶的回收站目錄。
回收站的文件也是可以下載到本地的。其實在這回收站只是一個具備了特殊含義的HDFS目錄。
注意:如果刪除的文件過大,超過回收站大小的話會提示刪除失敗 需要指定參數 -skipTrash ,指定這個參數表示刪除的文件不會進回收站
[root@bigdata01 hadoop-3.2.0]# hdfs dfs -rm -r -skipTrash /user.txt Deleted /user.txt
七、HDFS的安全模式
大家在平時操作HDFS的時候,有時候可能會遇到這個問題,特別是剛啟動集群的時候去上傳或者刪除文件,會發現報錯,提示NameNode處於safe mode。
這個屬於HDFS的安全模式,因為在集群每次重新啟動的時候,HDFS都會檢查集群中文件信息是否完整,例如副本是否缺少之類的信息,所以這個時間段內是不允許對集群有修改操作的,如果遇到了這個情況,可以稍微等一會,等HDFS自檢完畢,就會自動退出安全模式。
[root@bigdata01 hadoop-3.2.0]# hdfs dfs -rm -r /hadoop-3.2.0.tar.gz 2020-04-09 12:00:36,646 WARN fs.TrashPolicyDefault: Can't create trash directory: hdfs://bigdata01:9000/user/root/.Trash/Current org.apache.hadoop.hdfs.server.namenode.SafeModeException: Cannot create directory /user/root/.Trash/Current. Name node is in safe mode.
此時訪問HDFS的web ui界面,可以看到下面信息,on表示處於安全模式,off表示安全模式已結束
或者通過hdfs命令也可以查看當前的狀態
[root@bigdata01 hadoop-3.2.0]# hdfs dfsadmin -safemode get Safe mode is ON
如果想快速離開安全模式,可以通過命令強制離開,正常情況下建議等HDFS自檢完畢,自動退出
[root@bigdata01 hadoop-3.2.0]# hdfs dfsadmin -safemode leave Safe mode is OFF
此時,再操作HDFS中的文件就可以了。
八、HDFS讀寫流程
1、HDFS寫流程
2、HDFS讀流程