hadoop学习——hdfs指定tmp目录中内容的介绍
1、格式化
已经知道,当执行hadoop
格式化指令时,会在指定的tmp
目录下,生成dfs
目录。它下边具体如下:
[root@hadoop01 dfs]# ls
data name namesecondary
dfs/data
目录,是datanode
节点存储数据块的目录。
dfs/namesecondary
目录,对于以后集群中是没有用处的,只有伪分布式
模式时才会有这个。所以不用关心这个。
dfs/name
目录,该目录会存储着namenode
元数据信息。当格式化后,启动hdfs
前,在dfs/name/current
目录下,会生成一个最初的fsimage_0000000000000000000
和类似的文件。具体如下:
[root@hadoop01 current]# ls
fsimage_0000000000000000000 fsimage_0000000000000000000.md5 seen_txid VERSION
fsimage
该文件存储的是当前id前的快照数据,包括目录结构、节点信息等。fsimage
存储的是整个HDFS
的状态,元数据
存储在fsimage
文件中 。
带md5
的文件存储的就是对应的同名不带md5
的fsimage
文件的验证和,如果修改了fsimage
文件,可以通过md5
文件校验和,如果两者不同,则表示已修改。
对文件 md5校验和 可以输入如下命令:
md5sum fsimage_0000000000000000000
如果动了该文件,则namenode
启动不成功。
还有一个seed_txid
记录是最新的edits_inprogress
文件末尾的数字。edits
开头的文件,只有在启动后,才会出现。
格式化的危险
当执行格式化之后,相当于把tmp
下的内容清除掉,以前的数据将不存在,另外重新更新了clusterID
,该clusterID
表示的是当前namenode
的标识,如果它变了,那原本连接该namenode
的datanode
们将找不到它,当然可以将新的clusterID
更新到每个datanode
里,即可重新连接。
namespaceID=1702901649
clusterID=CID-47d78669-ad45-4fba-88d8-b523754ffab6 //namenode的标识
cTime=0
storageType=NAME_NODE
blockpoolID=BP-18504127-172.16.158.251-1544140849368
layoutVersion=-63
2、启动后
当启动hdfs
后,首先会在dfs/name
下生成一个in_use.lock
,这个文件的作用可以防止在同一台服务器上启动多个namenode
,避免管理紊乱。如下:
[root@hadoop01 name]# ls
current in_use.lock
当启动hdfs
后还会在name/current
路径下,生成edits
文件。如下:
[root@hadoop01 current]# ls
edits_0000000000000000001-0000000000000000002 fsimage_0000000000000000000 seen_txid
edits_inprogress_0000000000000000003 fsimage_0000000000000000000.md5 VERSION
edit
文件存储HDFS
的操作记录,每次有事务操作时,edits
会存储,相当于zookeeper
的事务log
文件。
初次启动hdfs
时,会有一个默认的edits
和fsimage
的合并时间,达到1分钟之后会进行合并,之后就按照1小时的周期来进行合并。
文件的命名最后的序号是递增的,每次合并一次即会从上一次合并点到当前时间点合并成一个文件
在同目录下还有另一个文件即edits_inprogress_0000000000000000003
。该文件的作用是记录当前正在执行的事务文件 ,后边的编号3
是以上一次最大的txid+1
。只要有操作,就会写到这样的文件里。
当停止hdfs
再启动hdfs
时,底层会触发一次rollEdits
指令,会触发END_LOG
事务,才会在上一个文件中有END_LOG
名,然后生成一个新的edits
文件。
3、查看元数据文件
如果想查看该文件,不能直接打开,都是乱码,需要输入下面的命令才能查看:
hdfs oev -i edits_0000000000001 -o edits.xml
hdfs oiv -i fsimage_000000000012 -o fsimage.xml -p XML
其中-i
为输入文件,-o
为输出文件。表示将该文件转换成xml等可读的文件。如果转换成功后,打开同目录下的edits.xml
,打开成功后即可看到内容,具体如下:
<xml version="1.0" encoding="UTF-8">
<EDITS>
<EDITS_VERSION>-63</EDITS_VERSION>
<RECORD>
<OPCODE>OP_START_LOG_SEGMENT</OPCODE>
<DATA>
<TXID>5</TXID>
</DATA>
</RECORD>
<RECORD>
<OPCODE>OP_END_LOG_SEGMENT</OPCODE>
<DATA>
<TXID>6</TXID>
</DATA>
</RECORD>
</EDITS>
如上图,hdfs
有事务id的概念,当hdfs
每接收一个事务操作(比如:mkdir put mv),都会分配响应的事务id,然后写到edits
文件中。每生成一个这样的文件,edits
文件中都会以START_LOG
开头,当一个edits文件
写完后,会以END_LOG
结尾。即在START_LOG
到END_LOG
之间。
上传文件底层会拆分成如下事务:
1、OP_ADD将文件假如到指定的HDFS目录下,并以_copying结尾,表示此文件还未写完。
2、ALLOCATE_BLOCK_ID为文件分配块ID
3、SET_GENSTAMP_V2为块生成时间戳版本号,是全局唯一的。
4、ADD_BLOCK写块数据。
5、OP_CLOSE,表示块数据写完
6、OP_RENAME_OLD将文件重命名。
4、fsimage文件介绍
文件和目录的元数据信息持久化存储到fsimage
文件中,hdfs
每次启动时从中将元数据加载到内存中构建目录结构树,之后的操作记录在edit log
中,并定期将edit
与fsimage
合并刷到fsimage
中。loadFSImage(File curFile)用于从fsimage
中读入namenode
持久化的信息。fsimage
中保存的元数据信息格式如下,hdfs
加载和写入时都按照该格式进行:
1
2
3
4
5
ImageVersion
NameSpaceId
NumFiles
genStamp
–
Path
BlockNums
mtime
atime
–
BlokId
BlockSize
BlockNumBytes
StorgeInfo
genStamp
nsquota
dsquota
username
groupname
permission
具体如下:
ImageVersion Fsimage
文件的版本号,每生成一个新的Fsimage
文件,就会有一个版本号。
NameSpaceId
:namenode
的命名空间id,用于标识namenode
。每当执行一次格式执行令时,就会生成新的
NumFiles
:整个HDFS存储的文件数。
genStamp
:有目录创建的时间戳,块生成的时间戳。
path
:文件路径
BlockNums
:文件的块数量
mtime
:上传时间
atime
:访问时间
BlockId
:块编号
BlockSize
:切块大小(128MB)
BlockNumBytes
:块的实际大小
StorgeInfo
:块存储的datanode节点信息
nsquota
:目录的命名空间大小配合,默认是-1 表示目录可以无限存储
dsquota
:目录的磁盘空间存储配额,默认是-1
username
:目录的创建者
groupname
:目录创建者的属组
permission
:目录的权限
HDFS启动时,会将这些信息读入内存之后,构造一个文件目录结构树,将表示文件或目录的节点填入到结构中。
5、写入操作(从文件级别来看)
如果有写入操作,则先将操作写到edits
文件中。
如果edits
文件写成功了。再将操作更新到内存中。为了防止操作产生丢失。
在内存中写入成功后,会给客户端一个成功的反馈。
在达到触发条件 的时候,才会将操作更新到fsimage
。
内存中的元数据=edits
+fsimage
。
触发条件:
1、文件大小:在hdfs
中可以通过fs.checkpoint.size
(在core-site.xml
)控制文件的大小。这个属性默认是64m,意味着edits
文件如果达到64m
之后,就会触发合并。
2、定时更新:在hdfs
中可以通过fs.checkpoint.period
来控制更新时间,默认值是3600s
,意味着每隔1个小时进行合并。
3、hdfs
重启的时候,也会触发更新。–进入安全模式。