博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Netty(五):Netty中如何序列化数据
阅读量:6252 次
发布时间:2019-06-22

本文共 4079 字,大约阅读时间需要 13 分钟。

JDK提供了ObjectOutputStream和ObjectInputStream,用于通过网络对POJO的基本数据类型和图进行序列化和反序列化。该API并不复杂,而且可以被应用于任何实现了java.io.Serializable接口的对象。但是它的性能也不是非常高效的。在这一节中,我们将看到Netty必须为此提供什么。

一、JDK序列化

如果你的应用程序必须要和使用了ObjectOutputStream和ObjectInputStream的远程节点交互,并且兼容性也是你最关心的,那么JDK序列化将是正确的选择。下表列出了Netty提供的用于和JDK进行互操作的序列化类。

JDK序列化编解码器

CompatibleObjectDecoder和使用JDK序列化的非基于Netty的远程节点进行互操作的解码器

CompatibleObjectEncoder 和使用JDK序列化的非基于Netty的远程节点进行互操作的编码器
ObjectDecoder 构建于JDK 序列化之上的使用自定义的序列化来解码的解码器;当没有其他的外部依赖时,它提供了速度上的改进。否则其他的序列化实现更加可取
ObjectEncoder 构建于JDK 序列化之上的使用自定义的序列化来编码的编码器;当没有其他的外部依赖时,它提供了速度上的改进。否则其他的序列化实现更加可取

二、使用JBoss Marshalling 进行序列化

如果你可以自由地使用外部依赖,那么JBossMarshalling将是个理想的选择:它比JDK序列化最多快3倍,而且也更加紧凑。在JBossMarshalling官方网站主页上的概述中对它是这么定义的:

JBoss Marshalling是一种可选的序列化API,它修复了在JDK序列化API中所发现的许多问题,同时保留了与java.io.Serializable及其相关类的兼容性,并添加了几个新的可调优参数以及额外的特性,所有的这些都是可以通过工厂配置(如外部序列化器、类/实例查找表、类解析以及对象替换等)实现可插拔的。

Netty通过下表所示的两组解码器/编码器对为Boss Marshalling 提供了支持。第一组兼容只使用JDK序列化的远程节点。第二组提供了最大的性能,适用于和使用JBoss Marshalling的远程节点一起使用。

JBoss Marshalling 编解码器

CompatibleMarshallingDecoder 与只使用JDK 序列化的远程节点兼容

MarshallingDecoder 适用于使用JBoss Marshalling 的节点。这些类必须一起使用。

以下代码清单展示了如何使用MarshallingDecoder 和MarshallingEncoder。同样,几乎只是适当地配置ChannelPipeline罢了。

使用JBoss Marshalling

public class MarshallingInitializer extends ChannelInitializer
{ private final MarshallerProvider marshallerProvider; private final UnmarshallerProvider unmarshallerProvider; public MarshallingInitializer(UnmarshallerProvider unmarshallerProvider, MarshallerProvider marshallerProvider) { this.marshallerProvider = marshallerProvider; this.unmarshallerProvider = unmarshallerProvider; } @Override protected void initChannel(Channel channel) throws Exception { ChannelPipeline pipeline = channel.pipeline(); pipeline.addLast(new MarshallingDecoder(unmarshallerProvider));// 添加MarshallingDecoder以将ByteBuf 转换为POJO pipeline.addLast(new MarshallingEncoder(marshallerProvider));// 添加MarshallingEncoder 以将POJO转换为ByteBuf pipeline.addLast(new ObjectHandler());// 添加ObjectHandler,以处理普通的实现了Serializable 接口的POJO } public static final class ObjectHandler extends SimpleChannelInboundHandler
{ @Override public void channelRead0(ChannelHandlerContext channelHandlerContext, Serializable serializable) throws Exception { // Do something } }}

三、通过Protocol Buffers 序列化

Netty序列化的最后一个解决方案是利用Protocol Buffers的编解码器,它是一种由Google公司开发的、现在已经开源的数据交换格式。可以在https://github.com/google/protobuf找到源代码。

Protocol Buffers 以一种紧凑而高效的方式对结构化的数据进行编码以及解码。它具有许多的编程语言绑定,使得它很适合跨语言的项目。表11-10 展示了Netty为支持protobuf 所提供的ChannelHandler实现。

Protobuf 编解码器

ProtobufDecoder 使用protobuf对消息进行解码

ProtobufEncoder 使用protobuf对消息进行编码
ProtobufVarint32FrameDecoder 根据消息中的Google Protocol Buffers 的“Base 128 Varints整型长度字段值动态地分割所接收到的ByteBuf
ProtobufVarint32LengthFieldPrepender 向ByteBuf 前追加一个Google Protocal Buffers 的“Base128 Varints”整型的长度字段值

在这里我们又看到了,使用protobuf只不过是将正确的ChannelHandler添加到ChannelPipeline 中,如下代码所示。

使用protobuf

public class ProtoBufInitializer extends ChannelInitializer
{ private final MessageLite lite; public ProtoBufInitializer(MessageLite lite) { this.lite = lite; } @Override protected void initChannel(Channel ch) throws Exception {   ChannelPipeline pipeline = ch.pipeline();   pipeline.addLast(new ProtobufVarint32FrameDecoder());// 添加ProtobufVarint32FrameDecoder以分隔帧   pipeline.addLast(new ProtobufEncoder()); // 添加ProtobufEncoder以处理消息的编码   pipeline.addLast(new ProtobufDecoder(lite));// 添加ProtobufDecoder以解码消息   pipeline.addLast(new ObjectHandler());// 添加ObjectHandler以处理解码消息 } public static final class ObjectHandler extends SimpleChannelInboundHandler
{ @Override public void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception { // Do something with the object } } }

由Netty专门的解码器和编码器所支持的不同的序列化选项:标准JDK序列化、JBoss Marshalling以及Google的Protocol Buffers。

转载地址:http://yaysa.baihongyu.com/

你可能感兴趣的文章
Android之Http通信——3.Android HTTP请求方式:HttpURLConnection
查看>>
hdu 5071 Chat(模拟)
查看>>
【转】 测试人员的职业规划 --整理标注
查看>>
C++智能指针--weak_ptr
查看>>
struts2的坑以及tomcat的一些常识
查看>>
HDURevenge of Segment Tree(第二长的递增子序列)
查看>>
Json数组操作小记 及 JSON对象和字符串之间的相互转换
查看>>
Linux服务器时间相关命令记录
查看>>
常量,字段,构造方法 调试 ms 源代码 一个C#二维码图片识别的Demo 近期ASP.NET问题汇总及对应的解决办法 c# chart控件柱状图,改变柱子宽度 使用C#创建Windows服...
查看>>
视频支持拖动进度条播放的实现(基于nginx)
查看>>
图文详解AO打印(端桥模式)(转)
查看>>
安装 directx sdk 出现 S1023 解决
查看>>
BZOJ2037: [Sdoi2008]Sue的小球(区间DP)
查看>>
Git-命令行-删除本地和远程分支
查看>>
SUPERSOCKET.CLIENTENGINE 简单使用
查看>>
第 7 章 异步输入输出
查看>>
ASP.NET应用使用Nginx做负载均衡遇到的一个问题
查看>>
Chapter 5 Blood Type——5
查看>>
在JSON中遇到的一些坑
查看>>
本文将介绍“数据计算”环节中常用的三种分布式计算组件——Hadoop、Storm以及Spark。...
查看>>