hadoop2.2原理:分析HDFS的文件读写
File Read
程序举例:
public class FileRead {
public static void main(Sting[] args) throws Exception {
Configuration conf = new Configuration();
FileSystem fs = FileSystem.get(conf);
InputStream in = new InputStream();
in = fs.open(new Path(args[0]));
IOUtils.copyBytes(in, System.out, 4096, false);
IOUtils.closeStream(in);
}
}
过程分析:
(1)open
当client读取文件时,在FileSystem ojbect上调用open()方法,而FileSystem是HDFS的一个instance;
从上述程序中可见:
line5 得到FileSystem的instance
line7 调用FileSystem上的open()方法
(2)get block location
随后,HDFS通过RPC(Remote Procedure Call)来呼叫namenode, 来获得the locations of the blocks for the first few blocks, 对于每一个block, namenode会返回有此block的datanode 的 address, 而且datanode会根据Network Topology被重新排序;
获取locations以后,DFS会返回一个FSDataInputStream给client来读取数据, FSDataInputStream会依次wrap一个DFSInputStream来管理datanode和namenode的I/O,DFSInputStream上同时也存储了first few datanode 的address;
(3)read
client 在FSDataInputStream上call read(), 则DFSInputStream会连接存储第一个block的最近的datanode, 之后不停地call read()方法从datanode读取数据到client, 当到达block的末尾,DFSInputStream会关闭与此datanode的连接, 然后找到存储下一个block的datanode, 依次往复...
(4) DFSInputStream
DFSInputStream按顺序读入每一个packet的最近的一个block, 每读一个block都要重新和一个datanode建立连接;
DFSInputStream同时会和namenode保持连接,来重新获取下一个packet的blocks所在的datanode的locations
(5)FSDataInputStream
FSDataInputStream 是client和datanode连接的中介, client call read() methods 都通过FSDataInputStream来调用DFSInputStream
(6)容错
在读取数据的过程中遇到的错误主要有两类:
1. DFSInputStream和datanode 的communication出现错误, 此时DFSInputStream会尝试连接保存此packet的下一个block所在的datanode中最近的一个, 同时会记录此datanode, 防止读取下一个block是再次从该datanode上读取;
2. DFSInputStream checksum data from datanode时,发现损坏的数据块, 则它会在DFSInputStream尝试从另一个datanode读取此packet的下一个block副本之前报告给namenode;
File Write
程序举例:
import org.apache.hadoop.fs.FileSystem;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.conf.Configuration;
public class CreateDir {
public static void main(String[] args) throws Exception {
Configuration conf = new Configuration();
String dst = args[0];
FileSystem fs = FileSystem.get(conf);
fs.create(new Path(dst));
}
}
过程分析:
(1)create
当client 写入文件时, 在FileSystem object上调用create()方法, FileSystem是HDFS的一个instance;
(2) create new file in filesystem's namespace
DFS 通过Remote Procedure Call 来call namenode, namenode会在filesystem的namespace产生一个新的文件, 新建文件之前,nanemode会做一些列检查,包括client是否有create file的permission, 要create的文件是否已经存在, 若检查没有通过,则抛出IOException;
create file以后,DFS会返回一个FSDataOutputStream给client来写文件, FSDataInputStream会wrap一个DFSOutputStream来与namenode和datanode交流;
(3) client write data
client开始写入数据到文件时,DFSOutputStream会将待写入的数据split into 很多packets, 这些packet会被写入一个内部队列data queue, DFSOutputStream维护此data queue;
这个data queue将被DataStreamer所用,DataStreamer主要负责向namenode发出申请,来为新的packet的block副本分配合适的datanode, namenode会挑选出合适的datanodes来存储这些data blocks;
存储这个packet的blocks的datanode会组成一个pipeline, 假设每个packet的block的replication level是3, 则此pipeline由3个datanode组成。
DataStreamer将此packet导入pipeline的第一个datanode, 该datanode存储此packet之后forward it to 第二个datanode, 同样地,第二个datanode存储此packet, forward to 第三个datanode;
(4) 容错
从(3)中我们知道DFSOutputStream维护着一个data queue, 此外,
DFSOutputStream还维护一个ack queue(acknowledged), 当一个packet已经被所有在pipeline中的datanode acknowledged, 则,此packet将会从ack queue中移走;
如果写数据时,一个datanode 写入失败,则会发生以下动作:
首先, pipeline会关闭,所有在ack queue中的packets会被添加到data queue前面,以保证下游的datanode不会丢失任何packets, 当前已写入datanode的数据块会被标识, 而写入坏的datnode中的部分数据会在此datanode recover以后被删除;
failed的datanode将从pipeline中移走, namenode 会notice到这些,会重新分配一个datanode来组成新的pipeline; 下一个packet的block不会受到影响;
当写入一个block时若大量的datanode failed,只要满足dfs.replication.min(default is 1), 则此写入就不会失败,block会被复制并同步到cluster上的datanode中,知道达到dfs.replication所设的数目(默认是3)
(5)数据写入的收尾阶段
当client完成数据写入是,client会调用在FSDataOutputStream 上的close()。 此动作会在给namenode发送file完成写入的信号之前flushs所有剩余的packets到datanode pipeline并等待acknowledge;
因为DataStreamer之前曾为所有的packets向namenode申请过block locations, 故namenode已经知道此文件由哪些blocks组成。
hadoop2.2原理:分析HDFS的文件读写的更多相关文章
- HDFS API 文件读写代码演示
一:准备工作 1.新建class类 2.开启HDFS服务 3.将配置文件拷贝进resources路径 方便了Configuration的读取配置. 二:读出HDFS文件系统中的文件到控制台 4.读出在 ...
- 012 HDFS API 文件读写代码演示
一:准备工作 1.新建class类 2.开启HDFS服务 3.将配置文件拷贝进resources路径 方便了Configuration的读取配置. 二:读出HDFS文件系统中的文件到控制台 4.读出在 ...
- 【Hadoop】二、HDFS文件读写流程
(二)HDFS数据流 作为一个文件系统,文件的读和写是最基本的需求,这一部分我们来了解客户端是如何与HDFS进行交互的,也就是客户端与HDFS,以及构成HDFS的两类节点(namenode和dat ...
- 2、Hdfs架构设计与原理分析
文章目录 1.Hadoop架构 2.HDFS体系架构 2.1NameNode 2.1.1元数据信息 2.1.2NameNode文件操作 2.1.3NameNode副本 2.1.4NameNode心跳机 ...
- Junit 注解 类加载器 .动态代理 jdbc 连接池 DButils 事务 Arraylist Linklist hashset 异常 哈希表的数据结构,存储过程 Map Object String Stringbufere File类 文件过滤器_原理分析 flush方法和close方法 序列号冲突问题
Junit 注解 3).其它注意事项: 1).@Test运行的方法,不能有形参: 2).@Test运行的方法,不能有返回值: 3).@Test运行的方法,不能是静态方法: 4).在一个类中,可以同时定 ...
- Hadoop2源码分析-HDFS核心模块分析
1.概述 这篇博客接着<Hadoop2源码分析-RPC机制初识>来讲述,前面我们对MapReduce.序列化.RPC进行了分析和探索,对Hadoop V2的这些模块都有了大致的了解,通过对 ...
- 大数据【二】HDFS部署及文件读写(包含eclipse hadoop配置)
一 原理阐述 1' DFS 分布式文件系统(即DFS,Distributed File System),指文件系统管理的物理存储资源不一定直接连接在本地节点上,而是通过计算机网络与节点相连.该系统架构 ...
- [置顶] Hadoop2.2.0中HDFS的高可用性实现原理
在Hadoop2.0.0之前,NameNode(NN)在HDFS集群中存在单点故障(single point of failure),每一个集群中存在一个NameNode,如果NN所在的机器出现了故障 ...
- HDFS 文件读写过程
HDFS 文件读写过程 HDFS 文件读取剖析 客户端通过调用FileSystem对象的open()来读取希望打开的文件.对于HDFS来说,这个对象是分布式文件系统的一个实例. Distributed ...
随机推荐
- 【html】【11】函数名称约束规范
一.匈牙利命名法: [不推荐]基本原则是:变量名=属性+类型+对象描述,其中每一对象的名称都要求有明确含义,可以取对象名字全称或名字的一部分.要基于容易记忆容易理解的原则.保证名字的连贯性是非常重要的 ...
- 基础之ThreadStatic
public class Bean { public Bean() { } public static String Current { get { if (guid == null) guid = ...
- angular2 select change 事件
刚开始这是啥?(wrong!!! change事件会在 选择option行为 之前执行prodDirId,是取不到选择后正确的id值的,取得是选择行为前prodDirId的值(有试过setTi ...
- 再也不要看到Eclipse万恶的arg0,arg1提示
不知道大家跟我是否一下,遇到arg的提示. @Override public void onDateChanged(DatePicker arg0, int arg1, int arg2, int a ...
- eclipse导入包的快捷键
在Eclipse里,写一个没有导入相应包的类名(这个类名已经完全写全,比如LayoutManager), 可以用ctrl+shift+M/Ctrl+Shift+o/Ctrl+1导入相应的包. 其中Ct ...
- cannot convert from '_TCHAR *' to 'char *'
Reference: Why can't convert TCHAR* to char* Need to Use Multi-Byte Character Set in project's setti ...
- ios中XPath的语法
在XML的读写中,我们知道有Xpath的语法 1.定位节点:(/)代表绝对的路径,代表起始地位置.(//)表示文件中所有符合模式的元素都会被选出来,即使是处于树中不同的层级也会被选出来 2.KissX ...
- ajax、json一些整理(1)
1.请求text数据,在success事件中手动解析 前台: $.ajax({ type: "post", ...
- c#基础知识对比(面向对象)
private,protected,public和internal private:是完全私有的,只有本类自己能用[好比自己的老婆,只有你自己可以调用,其他谁都不可以] protected:可被外界看 ...
- VB6-图像分割利器 Microsoft Picture Clip控件
在医院做图像处理时碰到双面扫描仪,需要将扫描到的2张图像分割为一张并打印.在分割图像的过程中总是不得法,后来虽然有CBM666的指导,但给的方法也还是不太方便.无意中在翻一本vb书的时候看到了一个使用 ...