基于hbase+hdfs的小文件(图片)存储

图片文件一般在100k一下,质量好一些的在几百k,特殊的图像可能达到10m左右,如果直接存储在hdfs上会对namenode的内存造成很大的压力,因为namenode的内存中会存储每个文件或者目录的inode信息。但是如果存储在hbase中,hbase的单个cell超过100k就会造成后期压力。因此采用hdfs的sequenceFile存储文件,hbase存储文件在sequenceFile中的索引信息。

sequenceFile存储

  自hadoop2.7.3以后,sequenceFile的write有了一个新的参数:AppendIfExistsOption,实现了可以向现有的sequenceFile中追加数据。每次写入数据之前和之后都记录当前的拍偏移 writer.getLength(),分别记为startPos和endPos。

hbase索引存储

  将文件名称(文件唯一标识)作为rowkey,存储该文件所在的sequenceFile的名称,以及存储时记录的startPos和endPos。

文件读取

   给定文件名,从hbase中检索到文件存储在hdfs对应的sequenceFile的name(包含路径),以及在文件中的起止position。根据文件名和起止位置去hdfs读取文件内容。

代码如下:

/**
     * 创建表
     */
    public static void createTable() throws IOException{
        HBaseAdmin admin = HbaseInit.getHBaseAdmin();       
        HTableDescriptor tableDesc = new HTableDescriptor(TableName.valueOf(tableName));
        HColumnDescriptor fimalyDesc = new HColumnDescriptor("v");
        tableDesc.addFamily(fimalyDesc);       
        admin.createTable(tableDesc);
    }

  /**
     * 将指定的文件写入文件系统,并将索引写入hbase
     */
    public static void FileWriter(byte[] image, int count) throws IOException {

IntWritable key = new IntWritable();
        Text value = new Text((byte[]) image);

SequenceFile.Writer writer = null;
        Option optPath = SequenceFile.Writer.file(p);
        Option optKey = SequenceFile.Writer.keyClass(key.getClass());
        Option optVal = SequenceFile.Writer.valueClass(value.getClass());
        Option optExist = SequenceFile.Writer.appendIfExists(true);
        Option optCompress = SequenceFile.Writer.compression(CompressionType.RECORD);

try {
            writer = SequenceFile.createWriter(fs.getConf(), optPath, optKey, optVal, optExist, optCompress);

long time = System.currentTimeMillis();
            HTable table = HbaseInit.getTable(TableName.valueOf("imageIdx"));
            long startPos = 0;
            for(int i = 0; i<count; i++){                
                startPos = writer.getLength();
                writer.append(key, value);
                Put put = new Put(Bytes.toBytes(System.currentTimeMillis()+"/ddd/ddd.txt"));
                put.addColumn(Bytes.toBytes("v"), Bytes.toBytes("name"), Bytes.toBytes("/ddd/ddd.txt"));
                put.addColumn(Bytes.toBytes("v"), Bytes.toBytes("start"), Bytes.toBytes(startPos));
                put.addColumn(Bytes.toBytes("v"), Bytes.toBytes("end"), Bytes.toBytes(writer.getLength()));                   
                table.put(put);      
            }
            System.out.println("写入hdfs&hbase耗时: "+ (System.currentTimeMillis()-time));
        } catch (Exception e) {
            e.printStackTrace();
            logger.error(e);
        } finally {
            IOUtils.closeStream(writer);
        }
    }

/**
     * 读取指定rowkey对应的索引数据
     */
    public static HbaseStoryEntity GetIdx(String rowKey) throws IOException{        
        HTable table = HbaseInit.getTable(TableName.valueOf(tableName));
                
        Get get = new Get(Bytes.toBytes(rowKey));
        
        Result r = table.get(get);
        HbaseStoryEntity imageFile = new HbaseStoryEntity();
        for(Cell cell: r.listCells()){
            if(Bytes.toString(CellUtil.cloneQualifier(cell)).equals("name")){
                imageFile.setFileName(Bytes.toString(CellUtil.cloneValue(cell)));
            }else if(Bytes.toString(CellUtil.cloneQualifier(cell)).equals("start")){
                imageFile.setStartPos(Bytes.toLong(CellUtil.cloneValue(cell)));
            }else if(Bytes.toString(CellUtil.cloneQualifier(cell)).equals("end")){
                imageFile.setEndPos(Bytes.toLong(CellUtil.cloneValue(cell)));
            }
        }       
        return imageFile;
    }

/**
     * 按照索引数据从sequenceFileduq读取数据
     */
    public static void FileReader(HbaseStoryEntity imageIdx) throws IOException {

SequenceFile.Reader.Option optlen = SequenceFile.Reader.length(imageIdx.getEndPos());
        SequenceFile.Reader reader = new SequenceFile.Reader(fs.getConf(),
                SequenceFile.Reader.file(new Path(imageIdx.getFileName())), optlen);
        reader.seek(imageIdx.getStartPos());
        IntWritable key = new IntWritable();
        Text value = new Text();
        while (reader.next(key, value)) {
        fileutil.FileWriter("D://image3//"+System.currentTimeMillis()+".jpg", value.getBytes());
        }      
        reader.close();
    }

  

时间: 2024-11-12 13:35:04

基于hbase+hdfs的小文件(图片)存储的相关文章

基于mogileFS搭建分布式文件系统--海量小文件的存储利器

一.分布式文件系统    1.简介 分布式文件系统(Distributed File System)是指文件系统管理的物理存储资源不一定直接连接在本地节点上,而是通过计算机网络与节点相连.分布式文件系统的设计基于客户机/服务器模式.一个典型的网络可能包括多个供多用户访问的服务器.另外,对等特性允许一些系统扮演客户机和服务器的双重角色.例如,用户可以"发表"一个允许其他客户机访问的目录,一旦被访问,这个目录对客户机来说就像使用本地驱动器一样. 当下我们处在一个互联网飞速发展的信息社会,在

小文件的存储

对于小文件的存储,指小于16M的文件 import bson bson.binary.Binary() 功能: 将bytes格式字符串装换为mongodb的二进制存储格式 将文件存储到数据库中: #小文件存储方案 #直接装换为二进程格式插入到数据库 from pymongo import MongoClient import bson.binary conn = MongoClient("localhost", 27017) db = conn.image myset = db.pyt

基于mogileFS搭建分布式文件系统 适用于海量小文件的存储

一.分布式文件系统 1.简介 分布式文件系统(Distributed File System)是指文件系统管理的物理存储资源不一定直接连接在本地节点上,而是通过计算机网络与节点相连.分布式文件系统的设计基于客户机/服务器模式.一个典型的网络可能包括多个供多用户访问的服务器.另外,对等特性允许一些系统扮演客户机和服务器的双重角色.例如,用户可以"发表"一个允许其他客户机访问的目录,一旦被访问,这个目录对客户机来说就像使用本地驱动器一样. 当下我们处在一个互联网飞速发展的信息社会,在海量并

海量小文件存储与Ceph实践

海量小文件存储(简称LOSF,lots of small files)出现后,就一直是业界的难题,众多博文(如[1])对此问题进行了阐述与分析,许多互联网公司也针对自己的具体场景研发了自己的存储方案(如taobao开源的TFS,facebook自主研发的Haystack),还有一些公司在现有开源项目(如hbase,fastdfs,mfs等)基础上做针对性改造优化以满足业务存储需求: 一. 通过对若干分布式存储系统的调研.测试与使用,与其它分布式系统相比,海量小文件存储更侧重于解决两个问题: 1.

MogileFS + Nginx 实现基于CentOS7平台的分布式文件存储与访问

MogileFS是一个开源的分布式文件系统,Nginx是开源的4-7层web应用服务端以及反向代理服务端.本文基于CentOS7平台,进行MogileFS + Nginx的部署 MogileFS的一些注意事项 针对于MogileFS,有如下概念需要注意一下. MogileFS属于有中心节点形式的分布式文件系统,元数据默认存储在关系型数据库(MySQL)当中,在此处于单点,因此有必要对MySQL使用主从复制或者MHA. 按功能分为tracker,database,storage.其中tracker

海量小文件存储最优解决方案,杉岩数据MOS完美解决

面对千亿量级的小文件,存储系统压力山大 所谓小文件,指的是存储占用空间相对较小的文件,一般来说低于64MB的文件就可以被认定为小文件,而大量的小文件大小则在几KB到几十KB之间.在云计算.大数据业务中,文本.图片.音乐等是典型的小文件应用场景. 随着数字化创新的加速,组织内部的数据呈现出指数级增长的趋势,特别是小文件更是随着业务增长到一个巨大的量级.与大文件的存储不同的是,大量磁盘在小文件存储场景中的性能极低,单块企业级SATA磁盘如果全部存储4KB左右的小文件,带宽只有520KB/s,远远小于

一种基于HBase韵海量图片存储技术

针对海量图片存储,已有若干个基于Hadoop的方案被设计出来.这些方案在系统层小文件合并.全局名字空间以及通用性方面存在不足.本文基于HBase提出了一种海量图片存储技术,成功解决了上述问题.本文将介绍基于HBase海量图片存储技术方案,分析其原理及优势,该方案在城市交通监控中得到应用验证. 随着互联网.云计算及大数据等信息技术的发展,越来越多的应用依赖于对海量数据的存储和处理,如智能监控.电子商务.地理信息等,这些应用都需要对海量图片的存储和检索.由于图片大多是小文件(80%大小在数MB以内)

LOSF 海量小文件问题综述

1.LOSF问题概述 在互联网(尤其是移动互联网).物联网.云计算.大数据等高速发展的大背景下,数据呈现爆炸式地增长.根据IDC的预测,到2020年产生的数据量 将达到40ZB,而之前2011年6月的预测是35ZB.然而,社会化网络.移动通信.网络视频音频.电子商务.传感器网络.科学实验等各种应用产生的数 据,不仅存储容量巨大,而且还具有数据类型繁多.数据大小变化大.流动快等显著特点,往往能够产生千万级.亿级甚至十亿.百亿级的海量小文件,而且更多地 是海量大小文件混合存储.由于在元数据管理.访问

大数据【二】HDFS部署及文件读写(包含eclipse hadoop配置)

一 原理阐述 1' DFS 分布式文件系统(即DFS,Distributed File System),指文件系统管理的物理存储资源不一定直接连接在本地节点上,而是通过计算机网络与节点相连.该系统架构于网络之上,势必会引入网络编程的复杂性,因此分布式文件系统比普通磁盘文件系统更为复杂. 2' HDFS 借此,关于GFS和HDFS的区别与联系查看 我于博客园找到的前辈的博客>>http://www.cnblogs.com/liango/p/7136448.html HDFS(Hadoop Dis