文档章节

Hadoop Outline Part 3 (I/O - Avro)

woodo
 woodo
发布于 2014/09/01 17:55
字数 1217
阅读 58
收藏 0

Serialization Framework

Hadoop有一个可替换的serialization framework API. 一个序列化框架用一个Serialization的实现来表示。

WritableSerialization

WritableSerialization是对Writable类型的Serialization的实现。

package: org.apache.hadoop.io.serializer
public class WritableSerialization extends Configured 
                         implements Serialization<Writable> {
    static class WritableSerializer extends Configured 
                         implements Serializer<Writable> {
         @Override
         public void serialize(Writable w) throws IOException {}
    }

    static class WritableDeserializer extends Configured 
                                      implements Deserializer<Writable> {
        @Override
         public Writable deserialize(Writable w) throws IOException {}
    }

    @Override
    public Serializer<Writable> getSerializer(Class<Writable> c) {
         return new WritableSerializer();
    }
    
    @InterfaceAudience.Private
    @Override
    public Deserializer<Writable> getDeserializer(Class<Writable> c) {
        return new WritableDeserializer(getConf(), c);
    }
}


JavaSerialization

JavaSerialization是对Serializable类型的Serialization的实现。它使用标准的Java Object Serialization。尽管它有利于方便的使用标准java类型,但是Java的标准化,效率较差。

package: org.apache.hadoop.io.serializer

public class JavaSerialization extends Object implements Serialization<Serializable>{}


为什么不用Java Object Serialization?

1. Not Compact. 每次序列化,都要写入类的名字,同一个类的后续实列只引用第一个次出现的句柄。这不太适合随即访问,排序 ,切分。

2. Nor Fast. 每次需要创建新的实例,浪费空间。

3. Extensible. 这个可以有,支持演化的新类型。目前无法和writable支持。

4. Interoperational. 理论可行,但是目前只有Java实现。Writable 也是如此。


Avro

Avro是一个独立于编程语言的数据序列化系统,它使用接口定义语言(IDL)定义Schema,然后可以生成其他语言的原生代码。Avro Schema通常用JSON来编写,数据通常用二进制格式编码。

Avro有很强的Data Schema Resolution能力,就是说读数据和写数据的Schema不必完全相同,Avro支持数据演化。

和其他序列化系统(Thrift 和 google Protocol Buffers)相比, Avro的性能更好。


Avro的Datatype和Schema

Primitive Datatype

null, boolean,int,long,float,double,bytes,string

Complex Datatype

array,排过序的同类型对象集合

{ "name":"myarray","type":"array", "items":"long" }


map,未排序的k-v对,key必须是string,schema只定义value

{ "name":"mymap","type":"map", "values":"string" }


record, 类似于struct,这个在数据格式中非常常用。

{  "type":"record","name":"weather-record","doc":"a weather reading.",

    "fields":[

        {"name":"myint","type":"int"},

        {"name":"mynull","type":"null"}

    ]

}

enum,命名集合

{  "type":"enum",

    "name":"title",

    "symbols":["engineer","Manager","vp"]

}

fixed,固定8位无符号字节

{ "type":"fixed","name":"md5"}


union,Schema的并集,使用json数组标志。数据必须与并集的一个类型匹配。

[ "type":"int","type":"long",{"type":"array", "items":"long" }]

表示数据必须是int,long, 或者long数组中的一个。


Avro的演化,略。

问题:

Avro如何排序?

Avro如何splitable?

Object Container File

Avro的数据文件结构如下: 


文件头

    四字节, ASCII 'O', 'b', 'j', followed by 1.

    file metadata

    The 16-byte, randomly-generated sync marker for this file.

    All metadata properties that start with "avro." are reserved. 

    avro.schema contains the schema of objects stored in the file, as JSON data (required).

    avro.codec the name of the compression codec used to compress blocks, as a string.          Implementations are required to support the following codecs: "null" and "deflate". If codec is absent,      it is assumed to be "null". The codecs are described with more detail below.

     Required Codecs

      null

     The "null" codec simply passes through data uncompressed.


     deflate

     The "deflate" codec writes the data block using the deflate algorithm as specified in RFC 1951, and      typically implemented using the zlib library. Note that this format (unlike the "zlib format" in RFC            1950) does not have a checksum.


     Optional Codecs

     snappy

     The "snappy" codec uses Google's Snappy compression library. Each compressed block is followed        by the 4-byte, big-endian CRC32 


     checksum of the uncompressed data in the block.


一个和多个数据块data blocks.


A long indicating the count of objects in this block.

A long indicating the size in bytes of the serialized objects in the current block, after any codec is applied

The serialized objects. If a codec is specified, this is compressed by that codec.

The file's 16-byte sync marker.

Thus, each block's binary data can be efficiently extracted or skipped without deserializing the contents. The combination of block size, object counts, and sync markers enable detection of corrupt blocks and help ensure data integrity.


Avro Read/Write


Schema和数据访问可以用GenericRecord,也可以使用SpecificRecord,需要用到Avro-Tools来生成对象类

% hadoop jar /usr/lib/avro/avro-tools.jar compile schema /pair.avsc /home/cloudera/workspace/

Schema, namespace会被注入到生成类中.

{
  "namespace":"com.jinbao.hadoop.hdfs.avro.compile",
  "type":"record",
  "name":"MyAvro",
  "fields":[
    { "name":"name","type":"string" },
    { "name":"age","type":"int" },
    { "name":"isman","type":"boolean" }
  ]
}


代码如下 

public class AvroTest {

	private static String avscfile = "/home/cloudera/pair.avsc";
	private static String avrofile = "/home/cloudera/pair.avro";
	/**
	 * @param args
	 * @throws IOException 
	 */
	public static void main(String[] args) throws IOException {

		//schemaReadWrite();
		
		// WriteData();
		
		ReadData();
		
	}
	
	private static void schemaReadWrite() throws IOException {
		/// Read Schema from schema file
		Parser ps = new Schema.Parser();
		Schema schema = ps.parse(new File(avscfile));
		if(schema != null){
			System.out.println(schema.getName());
			System.out.println(schema.getType());
			System.out.println(schema.getDoc());
			System.out.println(schema.getFields());
		}
		
		/// construct a record.
		GenericRecord datum = new GenericData.Record(schema);
		datum.put("left", new String("mother"));
		datum.put("right", new String("father"));
		
		/// write to outputstream
		ByteArrayOutputStream out = new ByteArrayOutputStream();
		DatumWriter<GenericRecord> writer = new GenericDatumWriter<GenericRecord>(schema);
		Encoder encoder = EncoderFactory.get().binaryEncoder(out, null);
		writer.write(datum, encoder);
		encoder.flush();
		out.close();
		
		/// read from inputstream
		DatumReader<GenericRecord> reader =  new GenericDatumReader<GenericRecord>(schema);
		Decoder decoder = DecoderFactory.get().binaryDecoder(out.toByteArray(), null);
		GenericRecord record = reader.read(null, decoder);
		System.out.print(record.get("left"));
		System.out.print(record.get("right"));
		
	}
	
	public static void WriteData() throws IOException{
		Parser ps = new Schema.Parser();
		Schema schema = ps.parse(new File(avscfile));
		File file = new File(avrofile);
		
		DatumWriter<GenericRecord> writer = new GenericDatumWriter<GenericRecord>(schema);
		
		DataFileWriter<GenericRecord> fileWriter = new DataFileWriter<GenericRecord>(writer);
		
		fileWriter.create(schema, file);
		MyAvro datum = new MyAvro();
		for(int i = 0;i<5;i++){
			datum.setName("name1" + i);
			datum.setAge(10 + i);
			datum.setIsman( i % 2 == 0);
			
			fileWriter.append(datum);
		}
		
		fileWriter.close();
	}
	
	public static void ReadData() throws IOException{
		File file = new File(avrofile);
		DatumReader<GenericRecord> reader = new GenericDatumReader<GenericRecord>();
		DataFileReader<GenericRecord> fileReader = new DataFileReader<GenericRecord>(file,reader);
		
		Schema schema = fileReader.getSchema();
		
		System.out.println(fileReader.getSchema());
		
		GenericRecord record = null;
		MyAvro datum = null;
		while(fileReader.hasNext()){
			record = fileReader.next();
			System.out.println(record.toString());
			
			// Convert GenericRecord to SpecificRecord
			datum = (MyAvro) SpecificData.get().deepCopy(schema, record);
			System.out.println(datum.toString());
		}
		fileReader.seek(0);
		fileReader.sync(0);

		fileReader.close();
	}
}



© 著作权归作者所有

woodo
粉丝 5
博文 57
码字总数 32118
作品 0
朝阳
高级程序员
私信 提问
Apache Spark 2.4 内置的 Avro 数据源介绍

Apache Avro 是一种流行的数据序列化格式。它广泛用于 Apache Spark 和 Apache Hadoop 生态系统,尤其适用于基于 Kafka 的数据管道。从 Apache Spark 2.4 版本开始,Spark 为读取和写入 Avro...

Spark
2018/12/11
0
0
Apache Avro 1.4.1 发布

Avro(读音类似于[ævrə])是Hadoop的一个子项目,由Hadoop的 创始人Doug Cutting(也是Lucene,Nutch等项目的创始人)牵头开发。Avro是一个数据序列化系统,设计用于支持大 批量数据交换的...

红薯
2010/10/18
1K
0
【译】Apache Spark 2.4内置数据源Apache Avro

原文链接: Apache Avro as a Built-in Data Source in Apache Spark 2.4 Apache Avro 是一种流行的数据序列化格式。它广泛使用于 Apache Spark 和 Apache Hadoop 生态中,尤其适用于基于 Ka...

开源大数据
2018/12/05
0
0
Apache Avro as a Built-in Data Source in Apache Spark 2.4

Apache Avro 是一种流行的数据序列化格式。它广泛用于 Apache Spark 和 Apache Hadoop 生态系统,尤其适用于基于 Kafka 的数据管道。从 Apache Spark 2.4 版本开始(参见 Apache Spark 2.4 正...

开源大数据EMR
2019/04/12
0
0
多语言跨平台远程过程调用【Avro】

开始 Avro是Apache的Hadoop家族的项目之一。具有性能高、基本代码少和产出数据量精简等特点。不过这是他们宣传广告,我最近也分别研究了Avro和Protobuf。基本的测试代码,不吐不快。 安装 Ja...

震秦
2013/08/07
6K
7

没有更多内容

加载失败,请刷新页面

加载更多

OSChina 周日乱弹 —— 谨以此文怀念逝去的人

Osc乱弹歌单(2020)请戳(这里) 【今日歌曲】 今天没歌曲 手机党少年们想听歌,请使劲儿戳(这里) 今天是周六, 刚想开始写乱弹的时候, 翻到了巴叔新建的话题上, @ 巴拉迪维:宏哥,一路...

小小编辑
今天
28
4
判断php变量是否定义,是否为空,是否为真的一览表

使用 PHP 函数对变量 $x 进行比较 表达式 gettype() empty() is_null() isset() boolean : if($x) $x = ""; string TRUE FALSE TRUE FALSE $x = null; NULL TRUE TRUE FALSE FALSE var $x; N......

Grayk
今天
19
0
服务器监控

1. 服务器监控内容有哪些? 答: 主要有服务监控 和 流量监控 2. 监控重点是? 答: 是 磁盘 和 流量,cpu是浮动的,意义不大 3. 怎样 实现 监控? 答:将 服务器 分为:监控者 和 被监管协议...

杨凯123
昨天
246
0
Apollo开发指南

一、准备工作 二、本地启动 2.1 Apollo Config Service和Apollo Admin Service 2.2 Apollo-Portal 2.3 Java样例客户端启动 2.4 .Net样例客户端启动 三、开发 3.1 Portal 实现用户登录功能 3....

Ciet
昨天
307
0
英文词汇 计算机网络中的专业英语单词及其缩写

学习计算机网络时,会阅读相关的专业文献。对于文献中经常出现的缩写形式的专业名词,做了一些积累。现于此博文中做个简单的分享,希望能对后来人有所帮助,平稳地入门计算机网络。 注:博文...

志成就
昨天
186
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部