Hadoop学习(三)— hdfs : NameNode与DataNode的实现机制
2017-09-29 00:05
856 查看
http://blog.csdn.net/tracker_wjw/article/details/51245274
数据量越来越多,在一台PC的范围存不下了,那么就分配到更多的PC中,但是不方便管理和维护,因此迫切需要一种系统来管理多台机器上的文件,这就是分布式文件管理系统。分布式文件管理系统很多,Hadoop的HDFS只是其中一种。
HDFS主要分为两大角色,NameNode与DataNode,NameNode主要负责管理元数据,DataNode主要负责存储文件块。NameNode来管理datanode与文件块的映射关系。
一、NameNode的工作机制
当客户端想HDFS请求,上传的文件的时候,NameNode会先去检查,要上传文件的目录是否存在,不存在,则允许上传。得到允许和NameNode返回的DataNode信息后,客户端开始向DataNode写入block,而block的副本的复制(NameNode管理),与客户端上传是异步进行的。HDFS为了快速的响应客户端的请求,也为了安全性的考虑(NameNode管理所有datanode,namenode宕机或者损坏,内存中的数据丢失,datanode中的所有数据就会无效),为了防止这种情况的发生,NameNode是如何实现的?
当客户端请求namenode时,namenode会将客户端的数据进行分析,分配好datanode,并将信息记录在一个editslog的文件中,并将datanode信息返回给客户端,客户端得到信息后,开始写入,每完成一个block,客户端会发发送成功信息给namenode,namenode就会把editlog中的信息,加载进内存,这样即使断电或者宕机,namenode中内存的数据也可以恢复,其他客户端想要下载数据,也可以从内存中加载,实现了快速响应。
editlog的空间是有限的,集群运行时间编边长的时候,editlog写满后,hdfs会将editlog的数据写入fsimage,也就是fsimage中的数据是最全,而editlog是最近最新更新的数据,为了保证fsimage中的数据与内存中的数据保证一致性,当editlog写满时,editlog中数据就会与fsimage的信息做合并,刷到fsimage中。
editlog与fsimage的合并工作由secondnamenode来完成的。
当editlog与fsimage合并时,secondnamenode会进行checkpoint操作(合并),namenode产生新的editlognew,而停止向老editlog写入。secondnamenode会从namenode中下载editlog与faimage,进行合并,产生新的合并文件。合并完成后,上传到Namenode上,namenode就会把新的镜像文件替换老的fsimage,经editlognew重命名为editlog,一切恢复初始。
什么时候checkpoint?
1.fs.checkpoint.period 指定两次checkpoint的最大时间间隔,默认3600秒。
2.fs.checkpoint.size 指定edits log文件的最大值,一旦超过这个值则进行checkpoint,不管是否到达最大时间间隔。默认大小是64M。(配置参数写在hdfs-site.xml中)
元数据的存储形式:
所以,多小文件往HDFS中存,会浪费NameNode的元数据空间。
namenode宕机了,在恢复正常之前。hadoop集群还能正常提供服务吗?
hadoop2.x提供了高可用机制,可以有效解决这个问题。
二、DataNode的工作机制
datanode的工作机制相对简单,提供文件数据的存储服务,存储单位是文件块(block),对于文件内容而言,一个文件的长度大小是size,那么从文件的0偏移开始,按照固定的大小,顺序对文件进行划分并编号,划分好的每一个块称一个Block。HDFS默认Block大小是128MB。dfs.block.size可以配置block的大小。如果一个文件小于一个数据块的大小仍然占用一个block,并不占用整个数据块存储空间,但是在namenode中占用一条元数据。
dfs.replication参数配置副本数,默认3个。
block的存储位置:
/hadoop-2.4.1/data/dfs/data/current/BP-980638925-127.0.0.1-1460262510326/current/finalized
三、HDFS在Java客户端编写
[java] viewplain copy
package cn.hadoop.hdfs;
import java.io.FileOutputStream;
import org.apache.commons.io.IOUtils;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.FSDataInputStream;
import org.apache.hadoop.fs.FileStatus;
import org.apache.hadoop.fs.FileSystem;
import org.apache.hadoop.fs.Path;
import org.junit.Before;
import org.junit.Test;
/**
* hdfs的API调用
* @author hadoop123
*/
public class FileUtils {
FileSystem fs = null;
@Before
public void before() throws Exception{
Configuration conf = new Configuration();
fs = FileSystem.get(conf);
}
/**
* 文件下载
* @throws Exception
*/
@Test
public void download() throws Exception{
Path src = new Path("hdfs://Wang-HP:9000/jdk-7u65-linux-i586.tar.gz");
FSDataInputStream in = fs.open(src);
FileOutputStream out = new FileOutputStream("/home/hadoop123/jdk32.gz");
IOUtils.copy(in, out);
}
/**
* 文件下载 调用hdfs的api
* @throws Exception
*/
@Test
public void download2() throws Exception{
Path src = new Path("hdfs://Wang-HP:9000/jdk-7u65-linux-i586.tar.gz");
Path dst = new Path("/home/hadoop123/jdk123.gz");
fs.copyToLocalFile(src, dst);
}
/**
* 文件上传
* @throws Exception
*/
@Test
public void upload() throws Exception{
Path src = new Path("/home/hadoop123/jdk123.gz");
Path dst = new Path("hdfs://Wang-HP:9000/jdk.gz");
fs.copyFromLocalFile(src, dst);
}
/**
* 查看文件
* @throws Exception
*/
@Test
public void getFiles() throws Exception{
//遍历所有文件,是否递归遍历
// RemoteIterator<LocatedFileStatus> listFiles = fs.listFiles(new Path("hdfs://Wang-HP:9000/"), true);
// while (listFiles.hasNext()) {
// LocatedFileStatus file = listFiles.next();
// System.out.println(file.getPath().getName());
// }
//listStatus列出文件和文件夹的信息,但不能递归遍历
FileStatus[] listStatus = fs.listStatus(new Path("hdfs://Wang-HP:9000/"));
for (FileStatus fileStatus : listStatus) {
fileStatus.isDirectory(); //是否是文件夹
String name = fileStatus.getPath().getName();
System.out.println(name);
}
}
/**
* 创建文件夹
*/
@Test
public void mkdir()throws Exception{
fs.mkdirs(new Path("/a/b/c"));
}
/**
* 删除文件夹
*/
@Test
public void rmdir()throws Exception{
fs.delete(new Path("/a/b/c"), true);//删除目录c,无论是否有数据
}
}
相关文章推荐
- Hadoop学习(三)— hdfs : NameNode与DataNode的实现机制
- 大数据之路-Hadoop-5-HDFS原理解析及NameNode、DataNode工作机制
- Hadoop之HDFS架构(NameNode和DataNode)
- Hadoop学习-错误记录:namenode、datanode、secondarynamenode未启动
- Hadoop的namenode的管理机制,工作机制和datanode的工作原理
- Hadoop原理---HDFS中的NameNode和DataNode
- Hadoop源码学习笔记(5) ——回顾DataNode和NameNode的类结构
- hadoop学习笔记之start-all.sh 无法启动NameNode,DataNode
- Hadoop 之 数据流——客户端与HDFS,namenode和datanode 之间的数据流
- 云计算学习笔记---异常处理---hadoop问题处理ERROR org.apache.hadoop.hdfs.server.datanode.DataNode: java.lang.NullPoin
- Hadoop中DataNode与NameNode之间的心跳机制
- hdfs haadmin使用,DataNode动态上下线,NameNode状态切换管理,数据块的balance,HA下hdfs-api变化(来自学习资料)
- hadoop2.0的DataNode与NameNode交互机制相关代码分析
- hadoop学习笔记--NameNode和DataNode以及容错处理
- Hadoop学习笔记(二)--添加data节点和实现远程挂载HDFS
- 【Hadoop】HDFS三组件:NameNode、SecondaryNameNode和DataNode
- hadoop的hdfs中的namenode和datanode知识总结
- hadoop源码分析系列(七)——org.apache.hadoop.hdfs包完结篇——dataNode详解及总结
- 云计算学习笔记004---hadoop的简介,以及安装,用命令实现对hdfs系统进行文件的上传下载
- Hadoop RPC整个使用流程——以DataNode向NameNode注册为例