Hadoop的简介以及文件处理
HADOOP简介
一.大数据思维
1.什么是大数据思维
分而治之:把一个复杂的问题按一定的“分解”方法分为等价的规模较小的若干部分,然后逐个解决,分别找出各部分的中间结果,把各部分的中间结果组成整个问题的最终结果。
并行:提升速度的关键 分布式运行 计算与数据在一起 计算向数据移动
二.Hadoop的历史
1.三篇论文
GFS----HDFS
MapReduce---MapReduce
BigTable----HBase
2.Hadoop Models
Hadoop Common:基础型模块。RPC调用,Socket通信
Hadoop Distributed File System 分布式文件系统,用于存储大数据的信息
Hadoop YARN 资源协调框架
Hadoop MapReduce 大数据计算框架
Hadoop Ozone: 对象存储框架
Hadoop Submarine: 机器学习引擎
3.分布式文件系统
1.分布式文件系统架构
FS File System
文件系统是基于硬盘之上的一个文件管理的工具
我们用户操作文件系统可以和硬盘进行解耦
DFS Distributed File System:
分布式文件系统
将我们的数据存放在多台电脑上存储
分布式文件系统有很多,
HDFS是mapreduce计算的基础
2.分布式架构的原理
-
如何拆分
-
数据都是以字节数组的方式存放在硬盘上
-
如果我们将文件分成两份,相当于将字节数组分成两份
-
888 KB (909,312 字节)
-
444KB 454,656字节
-
444kB 454,656字节
-
-
如果我们能将这两个数组再合并到一起,文件就会恢复成原来的样子
-
如果文件特别大,需要切分成N份,相当于切分成了N个字节数组
-
如何拼接? 10 20 30 40
-
-
为了记录每个子块(子字节数组)所属的位置,可以记录子块在整个文件的偏移量
-
数组都有对应的索引(下标),可以快速的定位数据
-
-
-
拆分大小
-
拆分之后块的大小要一致
-
如果大小不一致,很难通过偏移量来计算它的位置
-
如果数据块不一致,在多节点中拉取数据的时间不一致
-
分布式计算每台机器计算出结果的时间要相对一致
-
进行分布式算法设计的时候,数据不统一,算法很难设计
-
-
在H1默认大小为64M,在H2及其以后,默认大小为128M
-
同一个文件中,所有块的大小要完全一致,除了最后一个块
-
不同文件中,块的大小可以不同
-
块的数量= Ceil(总大小/每块的大小);
-
1024M 100M 11块
-
10M 1M 10块
-
-
问题
-
切的太整齐了,将一个完整的数据切分到两个块
-
-
-
数据安全
-
将数据备份多份
-
默认每一个数据都有三个备份
-
数据备份数不成超过节点数
-
-
数据规则
-
HDFS中一旦文件被存储,数据不允许被修改
-
修改会影响偏移量
-
修改会导致数据倾斜
-
修改数据会导致蝴蝶效益
-
-
但是可以被追加,但是不推荐
-
一般HDFS存储的都是历史数据
-
3.节点划分
NameNode:管理节点
DataNode:存储数据
三.搭建伪分布式
1.克隆一台虚拟机
按照之前linux搭建方法:修改IP地址,修改主机名称
2.设置免密钥登录
ssh-keygen -t rsa -P '' -f ~/.ssh/id_rsa
ssh-copy-id root@192.168.61.200 ~/.ssh/id_rsa.pub (按照上一步设置的IP进行登录)
3.上传Hadoop压缩包并移动到指定路径下
tar -zxvf hadoop-2.6.5.tar.gz
mv hadoop-2.6.5 /opt/sxt
4.设置环境变量
vim /eyc/profile
添加Hadoop路径 export HADOOP_HOME=/opt/sxt/hadoop-2.6.5 (以实际安装路径为主)
export PATH=$JAVA_HOME/bin:$HADOOP_HOME/bin:$HADOOP_HOME/sbin:$PATH
5.修改配置文件
文件路径:/opt/sxt/hadoop-2.6.5/etc/hadoop
(1)修改关于jdk的配置文件
文件hadoop-env.sh中修改jdk安装路径 25行
文件mapred-env.sh中修改jdk安装路径 16行
文件yarn-env.sh中修改jdk安装路径 23行
(2)修改核心配置文件
core-site.xml文件中添加
<property>
<name>fs.defaultFS</name>
<value>hdfs://node01:9000</value>
</property>
<property>
<name>hadoop.tmp.dir</name>
<value>/var/sxt/hadoop/local</value>
</property>
hdfs-site.xml文件中添加
<property>
<name>dfs.replication</name>
<value>1</value>
</property>
<property>
<name>dfs.namenode.secondary.http-address</name>
<value>node01:50090</value>
</property>
6.格式化
hdfs namenode -format
7.启动
start-dfs.sh
8.访问
9.开始使用命令创建目录
hdfs dfs -mkdir -p /user/root
hdfs dfs -put apache-tomcat-7.0.61.tar.gz /user/root
hdfs dfs -D dfs.blocksize=1048576 -put jdk-7u67-linux-x64.rpm /user/root
Hadoop文件处理
一. 节点分类
- block(块)
就是数据被切分后的一部分,一般默认的大小是128 M,存储了我们文件的数据信息,将来使用文件的时候需要将多个block拼接到一起.
每一个block都有自己的元数据信息:属于哪个文件,偏移量是多少,大小是多少.
数据上传时块的大小和备份数可以设置,但是上传成功后的文件备份数可以被修改,文件大小不能被修改.
Block实际存放的节点被称之为DataNode(DN)
Block块的存储信息会统计到一个节点上,该节点称之为namenode(NN).
NameNode(NN)
1.功能:接受hdfs客户端数据对数据的请求,管理分布式文件系统的文件信息:分布式文件目录;管理文件目录与文件的对应关系;管理文件与块的映射关系
/user/root/hadoop.tar.gz
blk_1073741946
块存储的节点(dn1,dn3,dn5)
blk_1073741947
块存储的节点(dn1,dn4,dn5)
blk_1073741948
块存储的节点(dn2,dn3,dn5)
blk_1073741949
块存储的节点(dn2,dn4,dn5)
但是块与DN节点的映射是不会被保存的
防止集群启动之后又DN损坏,但是namenode不知道损坏的事情,导致namenode向客户端传递错误的存储信息,也有可能块是损坏的.
- 实时与DN保持心跳
启动时,收集DN汇报的自身存储的block信息;启动后,没三秒确定DN是否存活,如果失联超过十分钟,namenode会将失联DN上的block拷贝到其他节点上
- 数据存储的介质
完全基于内存,计算速度快
缺点:异常关闭或者正常关闭时.数据回丢失;当内存使用率达到100%的时候,整个集群处于无法工作的状态,HDFS特别害怕存储小文件也特别害怕将备份设置的特别小
Datanode(DN)
- 功能:DN直接与客户端交互数据,数据是不会与NN发生关系的;存储真实的数据文件信息;每一个数据文件信息都会对应一个元数据信息;可以通过元数据信息校验初数据块是否有损坏.
- 与namenode保持心跳
启动时 验证块的完整性 向namenode汇报自己的存储块的信息,每隔三秒向namenode发送心跳包,证明自己的存在.
- 数据存储介质 完全基于硬盘;数据的写入写出速度一定要快
SecondaryNameNode
主要解决掉电易失的问题:存日志和生成快照
1.日志文件:edits_000000001 历史日志记录
edits_inprogress_000000002 正在编制的日志文件
2.快照 fsimage 文件系统的快照
3.存放位置
/var/sxt/hadoop/pseudo/dfs/name/current
fsimage_0000000000000000004 当前集群快照
fsimage_0000000000000000004.md5 快照的md5验证文件
edits_0000000000000000001-0000000000000000004 已经被整理过的日志信息
edits_inprogress_0000000000000000009当前集群正在写入日志的文件
seen_txid 事务的编号
VERSION 当前集群的信息
- 持久化流程
当集群运行的过程中用户会执行很多的操作,这些操作都会被记录到edits文件中;
fsimage对应着当前系统镜像:开机:当我们启动集群时候,nn会将当前(上次关机时)的fsimage与最新的日志进行合并产生新的fsimage;关机:关机的时候,不需要关心内存中的fsimage,直接关机即可.
当达到阈值(检查点 checkpoint --ckpt)的时候,两者只要满足一条就会合并fsimage与edits;
fs.checkpoint.size 默认64M
fs.checkpoint.period 默认3600秒
当达到阈值的时候,secondaryNameNode会将NN的fsimage与edits文件拷贝到secondaryNN主机上,然后合并(从FSiamge的当前状态重新执行日志文件),然后生成fsimage.ckpt,然后将fsimage.ckpt拷贝到NN上,然后检查文件的完整性,修改fsimage.ckpt的名字为正确名字;拷贝NN的edits文件时,将edits_inprogress_0000011文件修改名字为 edits_0000011,同时创建新的日志文件 edits_inprogress_00000012,新的日志会被写入到 edits_inprogress_00000012
这样就解决了一些问题:
(1) 启动时间过长问题解决:现在启动最多需要执行64M的日志数据.
(2) 异常关机问题解决:因为现在有日志机制,所有不担心异常关机.
二. HDFS读写数据的流程
- 机架感应
一种检查DN节点是否空闲可用的策略;这里的可用更多的是考虑效率与安全
DN选择的方式:分布式文件系统内部上传数据-->当前上传节点为第一个DN节点(上传速度快);分布式文件系统外部上传数据-->选取一个资源足够业务部繁忙的节点为第一个DN节点(空闲节点).
第二个节点一般选择到与第一个节点不同机架的其他节点,可以有效的防止所有节点失效;第三个节点一般选择与第二个节点相同机架的其他节点-->效率高;如果超过3个节点及其以上,除了上述三个节点外随机选择其他节点.
- 写入数据
(1) 宏观概念
客户端需要上传一个文件到HDFS(分布式文件系统)
首先客户端会发送create请求到分布式文件系统,其接到请求后,通过RPC调用NameNode.create方法
NN首先去检查文件路径是否存在,是否有足够权限操作文等操作:如果检查失败,不符合条件,抛出异常给DFS;如果检查成功,符合条件,在NN上创建一个空的Entry对象,并给DFS返回成功信息;
DFS接收到成功信息后,为客户端创建一个FSDataOutPutStream对象
客户端使用FSDataOutPutStream开始上传文件的第一个块:向NN请求当前Block的存放位置,应该存放在那个节点(DN);NN根据文件的副本数和机架感知策略,选择对应副本数量的节点(node1,node2,node3);客户端开始和三个DN创建Socket通讯 client-->node1-->node2-->node3,这种模式被称之为管道(pipeline),很好的解决了IO阻塞的问题;
客户端开始读取要上传的文件到自己的内存中,并且在内存中构建缓冲区buffered(减少物理IO)
默认一个block的大小为128M,但是发送的数据的级别为packet(默认64K):客户端从缓存中取出一个packet,从client通过FSDataOutPutStream,传输给node1,并且设置一个ACK状态;当node1接受完毕后继续将数据传递给node2,ack继续向下传递;当node2接受完毕后继续将数据传递给node3,ack继续向下传递;当node3接受完毕后开始返回响应的状态;node2接受到状态并继续返回;node1接受到状态并继续返回;最终client接收到响应的状态,说明当前块传输完成;重复执行传递packet的操作,直到整个块都传递完成;告知DFS当前块传输完成;DFS通过RPC调用将当前块完成的信息传递给NN,NN将Entry中加入当前块的位置信息;继续按照以上的流程传递剩余的块;当整个文件都上传文成,客户端关闭FSDataOutPutStream
(2) 微观概念
Pipeline管道:正向传输数据;逆向传递响应
Block 块 文件传输标准 128M
Packet 包 块传输的标准 64K
Chunk 片 包传输的标准 512b
Checknum 片的校验码 4b
Buffered 缓冲区, 可以减少物理IO
操作流程:从缓冲区取出chunk大小的数据,然后计算checknum;将chunk和checknum都封装到packet中;当packet装满之后,将其放在dataqueue队列中,等待发送;DataStreamer从dataqueue里面按照顺序依次取出packet;将要发送的packet放入到ackqueue里面然后才开始发送;每一个dn节点接收到数据之后都会进行校验:如果完整继续向后传递,如果不完整直接但会false状态;返回给客户端,客户端接收到返回状态之后会去ackqueue查找对应的packet;将packet之后的数据重新挂载到dataqueue将会被重新发送;当发送数据的时候,DN节点lose,会向NN汇报DN节点失效,NN会记录下备份失衡;会将略过这个节点和后面的节点建立关联(node2lost,node1-->node3);DFS会认为传输时只要有一个节点有完整数据,这个数据就是完整的.
- 读入数据
客户端想读取服务器的文件/sxt/ly/tomcat.tar.gz
首先客户端将请求发送给dfs,dfs通过RPC调用namenode的open方法
namenode会查找改目录是否存在,用户是否有读取的权限
如果权限检测没有问题那么直接返回true给dfs,dfs创建输入流FsDataInputStream
从NN获取块的DN信息,然后直接从DN上读取数据即可,优先选择同机架不繁忙的节点
当把BLOCK读取到客户端后,最终合并成一个文件
- 权限管理
Hadoop的权限和Linux的权限格式是一样的,但是Hadoop的权限验证比较简单;首先他肯定会做权限校验,符合UGO的标准;但是你告诉HDFS你是谁他就默认为你是谁;阻止好人做错事,而不是阻止坏人做坏事
5.安全模式
当分布式文件系统启动的时候,首先会载入fsimage,然后执行edits日志对应的操作;让自己尽快恢复到关机前状态,但是现在只存放了元数据信息
namenode在等待datanode汇报块的信息,这个时候就进入到安全模式
安全模式下客户端不能对namenode执行写入 删除 重命名等操作
只能执行一些类似于 查看文件或者文件目录等操作
当block达到最小副本数时就认为这个块是安全的,当安全块达到一定比例就认为环境是安全的;但是如果有些块达不到最小副本数,就会将该块拷贝到其他节点上;结束安全模式,客户端可以正常去使用DFS了