Hadoop3-分布式文件系统2

来源:互联网 发布:淘宝超级店长有什么用 编辑:程序博客网 时间:2024/06/16 22:20


1.从Hadoop URI中读取数据

static{

URL.setURLStreamHandlerFactory(new FsUrlStreamHandlerFactory());

}


InputStream in=null;

try{

in=new URI("hdfs://host/path").openStream();

IOUtils.copyBytes(in,System.out,4096,false);

}finally{

IOUtils.closeStream(in);

}


$hadoop URLCathdfs://host/1.txt


2.通过FileSystem API读取数据

Configuration conf=new ();

FileSystem fs=FileSystem.get(URI.create(uri),conf); //uri给定的URI方案

InputStream in=null;

try{

in=fs.open(new Path(uri)); //open->FSDataInputStream

IOUtils.copyBytes(in,System.out,4096,false);

}finally{

IOUtils.closeStream(in);

}


$hadoop FileSystemCat hdfs://host/file.txt

//seek read


3.写入文件

public FSDataOutputStreamcreate(Path f) throwsIOException

//append

本地文件复制到Hadoop

InputStream in=new BufferedInputStream(new FileInputStream(localFilePath));

Configuration conf=new ();

FileSystem fs=FileSystem.get(URI.create(dst),conf);

OutputStream out=fs.create(new Path(dst),new Progressable(){

public void progress(){

System.out.print(".");

}

});

IOUtils.copyBytes(in,out,4096,true);


//FSDataOutputStream


目录:

boolean mkdirs(Path f)throws IOException


4.查询文件系统

文件元数据:FileStatus

文件元数据:文件名称,长度,块大小,备份,修改时间,所有者,权限


Configuration conf=new ();

FileSystem fs=...;

fs.getFileStatus(new Path("path"));


exists(Path f)


5.列出文件

FileStatus[] FileSystem.listStatus(Path f)

...(Path[] files)

...(Path[] files,PathFilter filter)


FileUtil.stat2Paths(statusList); //反向转换


6.文件模式

通配 globbing

public FileStatus[] globStatus(Path pathPattern)

public FileStatus[] globStatus(Path pathPattern,PathFilter filter)

返回路径相匹配的所有文件的FileStatus对象数组,并按路径排序。


PathFilter

publc boolean accept(Path path){

return !path.toString().matches(regex);

}


7.删除数据

FileSystem.delete(Path f,boolean recursive)



//DistributedFileSystem通过使用RPC调用namenode,确定文件起始

块的位置,对于每一个块,namenode返回存有该块复本的datanode

地址。

datanode根据它们与客户端距离排序,如果客户端本身就是datanode

并保存有相应数据块的一个复本时,该节点将从本地datanode中读取

数据。


DistributedFileSystem返回一个FSDataInputStream对象,给客户端

并读取数据。FSDataInputStream转而封装DFSInputStream对象,

该对象管理着datanode和namenode的I/O。


客户端对输入流调用read()方法。存储着文件起始块的datanode地址的

DFSInputStream随机连接距离最近的datanode。通过对数据流反复调用

read()方法将数据从datanode传输到客户端。到达块的末端时,

DFSInputStream会关闭与该datanode的连接,然后寻找下一个块的最佳

datanode。客户端只需读取连续的流。


客户端<- DFSInputStream <-datanode

询问namenode检索下一批所需块的datanode位置。

一旦客户端完成读取,就对FSDataInputStream调用close()方法。


故障时会尝试从最邻近的datanode读取数据,并记住故障datanode。

DFSInputStream通过校验和确认数据完整,如果损坏会通知namenode,

从其他datanode读取。


namenode告知客户端每个块中最佳的datanode,让客户的直接联系

datanode并检索数据。


两个节点间的带宽作为距离衡量标准。

两节点距离是它们到最近的共同祖先的距离总和。


文件写入剖析:

客户端通过DistributedFileSystem 对象调用create()创建文件

DistributedFileSystem对namenode创建一个RPC调用,在

件系统命名空间中创建一个新文件。

namenode执行各种检查确保文件不存在,检查客户端权限。

通过则为创建新文件记录一条记录,否则跑出IO异常。

DistributedFileSystem向客户端返回一个FSDataOutputStream

对象,客户端可以开始写入数据,FSDataOutputStream封装

一个DFSOutPutStream对象,负责处理datanode和namenode之

间的通信。

客户端写入数据时,DFSOutputStream将它分成一个个数据包,

并写入内部队列,数据队列(data queue)。

DataStreamer处理数据队列,它的责任是根据datanode列表来

要求namenode分配适合的新块来存储数据备份。datanodes构成

一个管线。

DataStreamer将数据包流式传输到管线的第一个datanode,该datanode

存储数据包并将它发送到管线第二个datanode,然后一次进行。


DFSOutputStream维护着内部的一个数据包队列来等待datanode的收到

确认回执,ack queue。当收到管道中所有datanode确认信息后,该数据包

会从确认队列删除。


写入期间故障:.....

p87-93