一、什么是Google Protocol Buffer(protobuf官方网站

下面是官网给的解释:

Protocol buffers are a language-neutral, platform-neutral extensible mechanism for serializing structured data. – think XML, but smaller, faster, and simpler.

协议缓冲区是一种和语言无关、平台无关的可扩展机制,用于序列化结构化的数据。相比于xml,它更小,更快,更简单。数据缓冲区常用语通信协议和数据存储。

二、ProtoBuf的性能

序列化测试对比:

Ser Time + Deser Time(ns)

下面两个网站是效率测试实验:

三、使用Intellij IDEA插件自动生成Java类

参考我的另一篇文章:Google Protocol Buffer 的使用(一)

四、Netty和protobuf整合

准备我们的proto文件

syntax = "proto3";
package com.netty.protobuf;
option java_outer_classname = "UserInfoProto"; //用户信息
message UserInfo{
//姓名
string name = 1;
//住址
repeated Address address= 2;
//年龄
uint32 age = 3;
} //用户常用住址
message Address{
string addressname = 1;
uint32 adressno = 2;
}

服务器中设置protobuf编码器和解码器

@Override
protected void initChannel(SocketChannel ch) throws Exception {
ChannelPipeline pipeline = ch.pipeline();
//protobuf解码器
pipeline.addLast(new ProtobufVarint32FrameDecoder());
pipeline.addLast(new ProtobufDecoder(UserInfoProto.UserInfo.getDefaultInstance()));
//protobuf编码器
pipeline.addLast(new ProtobufVarint32LengthFieldPrepender());
pipeline.addLast(new ProtobufEncoder());
pipeline.addLast(new NettyServerHandler());
}
  • ProtobufVarint32FrameDecoder是protobuf方式的解码器,用于解决TCP粘包和拆包问题
  • ProtobufDecoder 中设置我们的proto文件生成的实例,其实就是我们的目标Java类,设置方式为:UserInfoProto.UserInfo.getDefaultInstance()
  • ProtobufVarint32LengthFieldPrepender和ProtobufEncoder是protobuf方式的编码器

处理类中写protobuf数据

    @Override
public void channelActive(ChannelHandlerContext ctx) throws Exception {
LOGGER.info("client {} connected.", ctx.channel().remoteAddress());
UserInfoProto.UserInfo user = UserInfoProto.UserInfo.newBuilder()
.setName("server")
.setAge(18)
.addAddress(
UserInfoProto.Address.newBuilder()
.setAddressname("beijing 001")
.setAdressno(911))
.build();
ctx.writeAndFlush(user);
}
  • 这里通过UserInfoProto.UserInfo.newBuilder()使用的时间其类的建造者模式设置用户相关信息。
  • 再通过ChannelHandlerContext的writeAndFlush方法写用户数据。

处理器中读protobuf数据

    private int count = 0;
@Override
public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {
UserInfoProto.UserInfo message = (UserInfoProto.UserInfo) msg;
LOGGER.info("server received message {}:{}", ++count, message);
}
  • channelRead中的Object对象通过解码之后就是一个protobuf类对象,所以可以强转:UserInfoProto.UserInfo message = (UserInfoProto.UserInfo) msg;

五、注意事项(TCP读半包处理)

这里我们只是简单使用了netty自带的ProtobufVarint32FrameDecoder解码器来处理读半包问题,我们还可以自己继承ByteToMessageDecoder类实现一个定制化的解码器。比如我们使用Java客户端和C++服务器通过protobuf协议来通信时,就需要自己实现,同时还需要考虑大端、小端模式的转换问题。

Netty使用Google Protocol Buffer完成服务器高性能数据传输的更多相关文章

  1. 前端后台以及游戏中使用Google Protocol Buffer详解

    前端后台以及游戏中使用Google Protocol Buffer详解 0.什么是protoBuf protoBuf是一种灵活高效的独立于语言平台的结构化数据表示方法,与XML相比,protoBuf更 ...

  2. Google protocol buffer的配置和使用(Linux&&Windows)

    最近自己的服务器做到序列化这一步了,在网上看了下,序列化的工具有boost 和google的protocol buffer, protocol buffer的效率和使用程度更高效一些,就自己琢磨下把他 ...

  3. Google Protocol Buffer 的使用(一)

    一.什么是Google Protocol Buffer下面是官网给的解释:Protocol buffers are a language-neutral, platform-neutral exten ...

  4. 详解Python Google Protocol Buffer

    为什么要使用PB? PB(Protocol Buffer)是 Google 开发的用于结构化数据交换格式,作为腾讯云日志服务标准写入格式.因此用于写入日志数据前,需要将日志原始数据序列化为 PB 数据 ...

  5. Google Protocol Buffer 的使用和原理[转]

    本文转自: http://www.ibm.com/developerworks/cn/linux/l-cn-gpb/ Protocol Buffers 是一种轻便高效的结构化数据存储格式,可以用于结构 ...

  6. Google Protocol Buffer 的使用

    简介 Google Protocol Buffer( 简称 Protobuf) 是 Google 公司内部的混合语言数据标准,目前已经正在使用的有超过 48,162 种报文格式定义和超过 12,183 ...

  7. 学习Google Protocol buffer之概述

    XML这种属于非常强大的一种格式,能存储任何你想存的数据,而且编辑起来还是比较方便的.致命的缺陷在于比较庞大,在某些情况下,序列化和解析都会成为瓶颈.这种对于实时性很强的应用来说,就不太适合了,想象下 ...

  8. Google Protocol Buffer的安装与.proto文件的定义

    什么是protocol Buffer呢? Google Protocol Buffer( 简称 Protobuf) 是 Google 公司内部的混合语言数据标准. 我理解的就是:它是一种轻便高效的结构 ...

  9. Google Protocol Buffer 的使用和原理

    Google Protocol Buffer 的使用和原理 Protocol Buffers 是一种轻便高效的结构化数据存储格式,可以用于结构化数据串行化,很适合做数据存储或 RPC 数据交换格式.它 ...

随机推荐

  1. 什么是TOML?

    配置文件的使用由来已久,从.ini.XML.JSON.YAML再到TOML,语言的表达能力越来越强,同时书写便捷性也在不断提升. TOML是前GitHub CEO, Tom Preston-Werne ...

  2. CentOS 7 配置163源

    具体的操作步骤: 1.打开终端,输入su指令切换到root用户:su 2.切换到系统yum源的目录下,即:cd /etc/yum.repos.d 3.备份系统默认yum源(也可直接删除):mv Cen ...

  3. Windows Phone SplashScreen初始屏幕示例

    protected override void OnLaunched(LaunchActivatedEventArgs args) { if (args.PreviousExecutionState ...

  4. BooleanToColorConverter

    public class BooleanToColorConverter : IValueConverter { public object Convert(object value, Type ta ...

  5. Android零基础入门第46节:下拉框Spinner

    原文:Android零基础入门第46节:下拉框Spinner 上一期学习了GridView的使用,你已经掌握了吗?本期一起来学习Spinner的使用. 一.认识Spinner Spinner其实就是一 ...

  6. 【备忘】C#语言基础-2

    泛型 CollectionClass<ItemClass> items = new CollectionClass<ItemClass>(); items.Add(new It ...

  7. CPU的最小执行单位是线程,协程不需要qt支持...直接用现成的协程库就行了

    协程也就在I/O操作上才有优势,Qt事件循环,本事很多I/O已经是异步了,利用好异步(虽然都说异步有点反人类思维).因为CPU的执行最小单位是线程,协程也只是在其之上又调度而已. 我的意思是利用好异步 ...

  8. 避免用户重复点击按钮(使用Enable:=False,消息繁忙时会有堵塞的问题,只能改用Sleep)

    // 现象描述://    用户点击按钮后程序开始繁忙工作,这时候用户不知道是否成功,就继续点几次//    采用Enalbe = false ... = true的方式发现还会触发点击,分析原因如下 ...

  9. RtlAdjustPrivilege进程提权,权限ID对照表

    SeCreateTokenPrivilege            0x2 SeAssignPrimaryTokenPrivilege     0x3 SeLockMemoryPrivilege    ...

  10. 主要C++流派,看看你是哪一流

    1. 经典C++流:类是核心,例程多用C Runtime的,很少用模版,一般是正统教育的结果.2. 古典C流:基本上当C用,偶尔用用对象,不使用异常,喜欢怀旧.3. MFC流:秉承MFC的风格,主要使 ...