首页 >> 大全

HDFS(Hadoop Distribute File System)

2023-08-31 大全 34 作者:考证青年

一、基本概念

一句话概括:HDFS是分布式文件系统,作用是存储大数据文件,是领域最基础的部分。

二、HDFS的重要特性

一群屌丝机组成高富帅

1、主从架构

作为负责管理元数据,作为从节点存储block块数据

主从:通常是一主多从,主干活,从也干活,负责的分工不同

主备:通常是一主一备,主要解决的是单节点故障问题,主干活,从为

2、分块存储

大文件的存储问题:写要能写的而下,读的时候还要读的块,将文件分成block块分布式存储,理论上多大的文件都可以存储,分块后再读取的时候可以并行读取,速度会非常的块。一般.x版本的默认是128M

3、名称空间

名称空间是指对外有统一的文件路径和命名,形如:hdfs://:9000//a.txt,要上传的文件名和要上传的位置,要下载的文件名和下载的文件路径,统一规范(简单理解就是我们通过50070能够看到的文件结构)。

4、元数据

负责元数据的管理,(元数据通常可以理解为修饰数据的数据),hdfs中元数据主要指目录结构和文件的块信息

hdfs的存储规则是尽量不存储小文件,因为一条元数据理论 ,例如10W个1Kb的小文件存储的硬盘需要100M,而存储元数据的内存就需要15M。

5、数据存储

负责存储block块数据,负责真实数据的存储,启动后需要向进行心跳,并且需要汇报本地块信息。

主要是存储,也就是需要磁盘,所以多台廉价的屌丝机就可以组成一个强大的HDFS存储集群

6、副本机制

副本就是备份,考虑的是容灾的问题,默认每个block有3个副本,他们为相互为对方的副本。

机架感知(3副本机制)

7、一次写入多次读取 8、限额操作

数量限额
hdfs dfsadmin -setQuota 2 限定的文件的路径      # 给该文件夹下面设置最多上传两个文件,上传文件,发现只能上传一个文件
清除权限 -clrQuota空间限额
假如现在上传的一个文件的备份数是2 现在的空间不足256
假如上传的是129M的文件  那么至少是需要剩余空间512才可以上传文件到hdfs查看hdfs文件xiane
hdfs dfsadmin -setQuota 2 限定的文件的路径      # 给该文件夹下面设置最多上传两个文件,上传文件,发现只能上传一个文件

三、hdfs常用shell命令介绍

-ls
使用方法:hadoop fs -ls [-h] [-R] 
功能:显示文件、目录信息。
示例:hadoop fs -ls /user/hadoop/file1-mkdir
使用方法:hadoop fs -mkdir [-p] 
功能:在hdfs上创建目录,-p表示会创建路径中的各级父目录。
示例:hadoop fs -mkdir –p /user/hadoop/dir1-put
使用方法:hadoop fs -put [-f] [-p] [ -| .. ].  hadoop fs -put linux中文件的路径  hdfs上的路径
功能:将单个src或多个srcs从本地文件系统复制到目标文件系统。
-p:保留访问和修改时间,所有权和权限。
-f:覆盖目的地(如果已经存在)
示例:hadoop fs -put -f localfile1 localfile2 /user/hadoop/hadoopdir-get
使用方法:hadoop fs -get [-ignorecrc] [-crc] [-p] [-f]  hadoop fs -get hdfs中文件的路径  本地文件的路径hadoop fs -get /hadoop32/word.txt  /export
-ignorecrc:跳过对下载文件的CRC检查。
-crc:为下载的文件写CRC校验和。
功能:将文件复制到本地文件系统(linux上)。
示例:hadoop fs -get hdfs://host:port/user/hadoop/file localfile-appendToFile 
使用方法:hadoop fs -appendToFile  ... 
功能:追加一个文件到已经存在的文件末尾(将文件的内容加载到hdfs中已经存在的文件中)
示例:hadoop fs -appendToFile localfile  /hadoop/hadoopfile-chown
功能:改变文件的拥有者。使用-R将使改变在目录结构下递归进行。
示例:hadoop  fs  -chown  someuser:somegrp   /hadoop/hadoopfile-cp              
功能:从hdfs的一个路径拷贝hdfs的另一个路径
示例: hadoop  fs  -cp  /aaa/jdk.tar.gz  /bbb/jdk.tar.gz.2-mv                     
功能:在hdfs目录中移动文件
示例: hadoop  fs  -mv  /aaa/jdk.tar.gz  /-rm                
功能:删除指定的文件。只删除非空目录和文件。-r 递归删除。
示例:hadoop fs -rm -r /aaa/bbb/-df               
功能:统计文件系统的可用空间信息
示例:hadoop  fs  -df  -h  /-du 
功能:显示目录中所有文件大小,当只指定一个文件时,显示此文件的大小。
示例:hadoop fs -du /user/hadoop/dir1

四、HDFS的基本原理 1、概述

a、	NameNode是HDFS的核心。
b、	NameNode也称为Master。
c、	NameNode仅存储HDFS的元数据:文件系统中所有文件的目录树,并跟踪整个集群中的文件。
d、	NameNode不存储实际数据或数据集。数据本身实际存储在DataNodes中。
e、	NameNode知道HDFS中任何给定文件的块列表及其位置。使用此信息NameNode知道如何从块中构建文件。
f、	NameNode并不持久化存储每个文件中各个块所在的DataNode的位置信息,这些信息会在系统启动时从数据节点重建。
g、	NameNode对于HDFS至关重要,当NameNode关闭时,HDFS / Hadoop集群无法访问。
h、	NameNode是Hadoop集群中的单点故障。
i、	NameNode所在机器通常会配置有大量内存(RAM)。

2、概述

a、	DataNode负责将实际数据存储在HDFS中。
b、	DataNode也称为Slave。
c、	NameNode和DataNode会保持不断通信。
d、	DataNode启动时,它将自己发布到NameNode并汇报自己负责持有的块列表。
e、	当某个DataNode关闭时,它不会影响数据或群集的可用性。NameNode将安排由其他DataNode管理的块进行副本复制。
f、	DataNode所在机器通常配置有大量的硬盘空间。因为实际数据存储在DataNode中。
g、	DataNode会定期(dfs.heartbeat.interval配置项配置,默认是3秒)向NameNode发送心跳,如果NameNode长时间没有接受到DataNode发送的心跳, NameNode就会认为该DataNode失效。
h、	block汇报时间间隔取参数dfs.blockreport.intervalMsec,参数未配置的话默认为6小时.

3、HDFS的工作机制 3.1 写过程

1、datanode向namenode汇报自己的状态信息和块列表
2、client找到namenode,向namenode申请上传文件
3、namenode进行校验是否有权限上传,看是否有同名的文件 如果没加入覆盖则不允许上传
4、如果通过,则允许上传文件
5、假如现在的文件是129m 则会对文件进行切割,一个是128 一个是1
6、进行上传 先上传第一个block块,这时会问namenode传送到哪个datanode块上去 ,
7、namenode进行机架感知,选出一个datanode地址列表,并返回给客户端,比如node01、node03
8、这是client就会知道连接哪个datanode。然后建立管道,node01和node03之间也需要建立管道
9、会把block块再次拆分成64k的包然后上传,最后根据偏移量组装成一个新的文件
10、备份成功后会返回一个ack确认码
11、然后继续上传第二个block块

3.2读过程

1、申请下载,client向namenode询问 namenode中的namespace保存的是文件的名称和路径以及一些元数据信息
2、这样就会知道你所要下载的文件到底在那个datanode上面 但是有时候备份很多的话,就会根据网络拓扑图翻回最近的一个block块并且是状态好的
3、这样就会得到你需要的文件的地址列表,这样就会连接datanode,进行并行的读取,就会很快速的读取,集群做的够大,他的吞吐能力是非常的强的

五、HDFS的应用操作 1、HDFS的操作

1.1搭建开发环境

clouderahttps://repository.cloudera.com/artifactory/cloudera-repos/

org.apache.hadoophadoop-client2.6.0-mr1-cdh5.14.0org.apache.hadoophadoop-common2.6.0-cdh5.14.0org.apache.hadoophadoop-hdfs2.6.0-cdh5.14.0org.apache.hadoophadoop-mapreduce-client-core2.6.0-cdh5.14.0	

1.原始流对接操作--繁琐但灵活

/*** @ClassName StreamAccess* @Description stream流对接的方式上传下载数据*/
public class StreamAccess {//创建客户端对象FileSystem fs = null;//创建fs的4种方式@Beforepublic void createFS() throws IOException, URISyntaxException, InterruptedException {Configuration conf = new Configuration();//第一种方式 如果什么参数都不给,创建的是本地文件系统 file:///  hdfs  50070 9000// 9000是用来操作的 50070是用来看的//优先级  当前的配置  > 项目的classpath > 用户设置的hadoop/etc/hadoop/core-site.xml > 默认的core-default.xmlconf.set("fs.defaultFS","hdfs://node01:9000");System.setProperty("HADOOP_USER_NAME","root");fs = FileSystem.get(conf);//第二种方式(用的最多)fs = FileSystem.get(new URI("hdfs://node01:9000"),conf,"root");//第三种方式conf.set("fs.defaultFS","hdfs://node01:9000");fs = FileSystem.newInstance(conf);//第四种方式fs = FileSystem.newInstance(new URI("hdfs://node01:9000"),conf);}//上传@Testpublic void streamToHdfs() throws Exception {//得到本地的输入流FileInputStream inputStream = new FileInputStream(new File("d:/pom.xml"));//得到hdfs的输出流 要写文件FSDataOutputStream outputStream = fs.create(new Path("/hadoop32/1.txt"));//流对接IOUtils.copy(inputStream,outputStream);}//下载@Testpublic void streamDownLoad() throws Exception {//hdfs得到输入流FSDataInputStream inputStream = fs.open(new Path("/hadoop32/1.txt"));//得到本地文件的输出流inputStream.seek(346); // 从哪个位置开始下载FileOutputStream outputStream = new FileOutputStream(new File("d:/3.txt"));IOUtils.copy(inputStream,outputStream);}//获取hdfs上的所有文件及路径  hadoop fs -ls -R /@Testpublic void findAllFiles() throws Exception {RemoteIterator iterator = fs.listFiles(new Path("/"), true);// true为是否进行递归查询while (iterator.hasNext()) {//fileStatus是对文件或文件夹的所属数据信息LocatedFileStatus fileStatus = iterator.next();System.out.println(fileStatus.getPath());}}//遍历hdfs上所有的文件和文件夹@Testpublic void findAll() throws Exception { findFiles("/");}private void findFiles(String path) throws IOException {FileStatus[] fileStatuses = fs.listStatus(new Path(path));for (FileStatus fileStatus : fileStatuses) {//每一个文件或文件夹的所有数据if(fs.isDirectory(fileStatus.getPath())){//得到的就是文件夹System.out.println("d----"+fileStatus.getPath());findFiles(fileStatus.getPath().toString());}else{//得到的就是文件System.out.println("f----"+fileStatus.getPath());}}}//获取指定的block块@Testpublic void getBlock0() throws Exception {FSDataInputStream in = fs.open(new Path("/hadoop32/y.zip"));//如果path指定的是一个文件,那么数组返回的大小就是1FileStatus[] fileStatuses = fs.listStatus(new Path("/hadoop32/y.zip"));FileStatus fileStatus = fileStatuses[0];//返回当前文件所有block块的地址列表BlockLocation[] fileBlockLocations = fs.getFileBlockLocations(fileStatus, 0, fileStatus.getLen());/* for (BlockLocation fileBlockLocation : fileBlockLocations) {//得到的是每个块的信息System.out.println( fileBlockLocation.getLength()+" offset :"+  fileBlockLocation.getOffset());String[] hosts = fileBlockLocation.getHosts();//当前块hostfor (String host : hosts) {System.out.println("host"+host);}}*/BlockLocation fileBlockLocation = fileBlockLocations[1];//第二个block块的偏移量long offset = fileBlockLocations[1].getOffset();//注意长度的问题:第一个块的长度是128M 第二个块的长度是111M 所以就是从128M向后读了111M的数据,也就是从128M读取到239M的位置,这个长度是指239这个数值long length = offset+fileBlockLocations[1].getLength();byte[] b = new byte[4096];FileOutputStream os = new FileOutputStream(new File("d:/block1"));while(in.read(offset, b, 0, 4096)!=-1){os.write(b);offset += 4096;if(offset>length) {return;}};}@Afterpublic void close() throws Exception {//通常如果是get方式的话不建议关闭,如果是newInstance的话 建议关闭fs.close();}
}

1.3客户端操作--简单易操作

public class HDFSClient {FileSystem fs = null;//初始化hdfs文件系统@Beforepublic void createFS() throws Exception{Configuration conf = new Configuration();fs = FileSystem.get(new URI("hdfs://node01:9000"),conf,"root");//获取到所有datanode节点信息DatanodeInfo[] dataNodeStats = ((DistributedFileSystem) fs).getDataNodeStats();for (DatanodeInfo dataNodeStat : dataNodeStats) {System.out.println(dataNodeStat.getName());}}//文件的上传@Testpublic void copyFromLocalFile() throws Exception{//文件上传  参数1:是否会删除本地原文件 参数2:是否会覆盖掉hdfs上目标的文件 参数3:本地文件路径  参数4:目标hdfs文件路径fs.copyFromLocalFile(true,true,new Path("d:/Maven_Repository.zip"),new Path("/hadoop32"));}//文件的下载@Testpublic void copyToLocalFile() throws Exception {fs.copyToLocalFile(true,new Path("/hadoop32/Maven_Repository.zip"),new Path("d:/y.zip"));}@Testpublic void testMkdirAndDeleteAndRename() throws IllegalArgumentException, IOException {// 创建目录fs.mkdirs(new Path("/a1/b1/c1"));// 删除文件夹 ,如果是非空文件夹,参数2必须给值truefs.delete(new Path("/aaa"), true);// 重命名文件或文件夹fs.rename(new Path("/a1"), new Path("/a2"));}
}

关于我们

最火推荐

小编推荐

联系我们


版权声明:本站内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 88@qq.com 举报,一经查实,本站将立刻删除。备案号:桂ICP备2021009421号
Powered By Z-BlogPHP.
复制成功
微信号:
我知道了