`
朋在无锡
  • 浏览: 34794 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论

游戏开发中的protobuf自动解码DEMO

阅读更多

本人为游戏服务端开发者,开发中protobuf的解码操作比较麻烦,每次解码都需要写一大堆重复的代码,还需要处理错误,设计了一个工具类,现在将业务逻辑简化一下和除去业务敏感信息,发布出来,使用源码需要注意以下几点:

1.所有protobuf 消息基于 generatedMessage;

2.protobuf运行时需要配置protobuf.exe位置

3.反射比较耗费性能,设计中将反射等操作放在系统初始化进行,将结果放置到map中,业务运行时直接取出;.

4.开发中结合注解还能进一步简化配置,不需要添加class 到map中

5.对于编码错误,可能为第三方恶意尝试命令码,编码错误统一管理更加方便屏蔽.

解码代码如下:

package code;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import proto.gen.TestProto.MyMsgReq;

import com.google.protobuf.GeneratedMessage;

public class DecordDemo {
	private final static Map<Integer, Method> DECODE_METHODS_MAP = new HashMap<Integer, Method>();// 存储解码方法MAP
	private final static Map<Integer, Class<? extends GeneratedMessage>> DECODE_CLASSES = new HashMap<Integer, Class<? extends GeneratedMessage>>();// 存储类的map
	private final static int MY_MSG_REQ_CMD = 100;

	public static void main(String[] args) throws Exception {
		initDecode();
		MyMsgReq.Builder reqSrc = MyMsgReq.newBuilder().setId(1).setName("mine");
		MyMsgReq req = decode(MY_MSG_REQ_CMD, reqSrc.build().toByteArray());
		System.out.println(req.getId());
		System.out.println(req.getName());
	}

	/**
	 * 初始化 方法,系统启动时即将解码器反射好,业务逻辑时直接从MAP中查询出,解码
	 * */
	public static void initDecode() {
		addDecodeMethod(MY_MSG_REQ_CMD, MyMsgReq.class);
	}

	public static void addDecodeMethod(int cmd, Class<? extends GeneratedMessage> clazz) {
		try {
			Method m = clazz.getMethod("parseFrom", new Class[] { byte[].class });
			if (DECODE_METHODS_MAP.get(cmd) == null) {
				DECODE_METHODS_MAP.put(cmd, m);
			}
			if (DECODE_CLASSES.get(cmd) == null) {
				DECODE_CLASSES.put(cmd, clazz);
			}

		} catch (NoSuchMethodException | SecurityException e) {
			e.printStackTrace();
		}
	}

	/**
	 * 业务中调用
	 * 
	 * @throws Exception
	 * */
	@SuppressWarnings("unchecked")
	public static <T> T decode(int cmd, byte[] data) throws Exception {
		Method decodeMethod = DECODE_METHODS_MAP.get(cmd);
		Class<? extends GeneratedMessage> clazz = DECODE_CLASSES.get(cmd);
		if (decodeMethod == null || clazz == null) {
			throw new Exception("找不到对应解码方法");
		}
		T req;
		try {
			req = (T) decodeMethod.invoke(clazz, new Object[] { data });
		} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
			e.printStackTrace();
			throw new Exception("解码异常", e);
		}
		return req;
	}
}
protobuf代码如下:
package proto.gen;

message MyMsgReq {
	required int32 id = 1;
	optional string name = 2; //
}
0
1
分享到:
评论
1 楼 beykery 2014-12-31  
你还是看看jprotobuf吧,别折腾了

相关推荐

    protobufdemo

    标题中的"protobufdemo"指的是一个使用Google的Protocol Buffers(简称protobuf)编写的演示项目。Protocol Buffers是一种高效的数据序列化协议,它允许开发者定义数据结构,然后生成能够在各种编程语言中使用的代码...

    java生成protobufdemo直接运行

    在Java环境中,我们可以使用protobuf编译器来生成Java类,这些类可以轻松地进行数据编码和解码。 本教程将指导你如何使用Java直接运行protobuf demo,生成protobuf所需的Java类,并展示如何读取和写入protobuf数据...

    protobuf的c语言版本在嵌入式linux上的测试demo

    在这个“protobuf的c语言版本在嵌入式linux上的测试demo”中,我们重点关注的是如何在嵌入式Linux环境下使用protobuf的C库。嵌入式Linux系统通常资源有限,因此选择C语言版本的protobuf可以更好地适应这种环境。 ...

    ProtobufDemo

    4. **类型安全**:在编码和解码过程中,能自动进行类型检查,减少潜在错误。 总的来说,"ProtobufDemo"展示了如何使用Protobuf进行数据序列化和反序列化,这对于构建高效、可靠的网络通信系统或存储大量结构化数据...

    Protobuf应用实例

    在JAVA环境中,protobuf提供了方便的编解码功能,使得数据的序列化和反序列化变得简单而高效。 ### 1. Protobuf的基本概念 - **数据定义(.proto文件)**:protobuf的数据模型通过.proto文件来定义,包含了各种...

    Protobuf-net

    protobuf-net提供了一个易于使用的API,使得.NET开发人员能够快速地在应用程序中集成protobuf功能。 **protobuf的优势:** 1. **高效性**:protobuf生成的二进制格式比XML或JSON更小、更快,适合在网络传输和存储中...

    protobuf-demo-js:协议在JavaScript中缓冲演示

    标题中的“protobuf-demo-js”指的是Protocol Buffers(简称protobuf)的一个JavaScript实现示例。Protocol Buffers是一种高效的数据序列化协议,由Google开发,用于结构化数据的存储和通信。它提供了一种简单的方法...

    js_protobuf_demo

    标题 "js_protobuf_demo" 暗示我们正在讨论一个基于JavaScript的项目,它与Protocol Buffers(简称protobuf)有关,protobuf是Google开发的一种数据序列化协议,常用于高效地存储和传输结构化数据。这个项目很可能是...

    netty+protobuf (整合源代码)

    处理器链中,我们可以自定义一个 ChannelInboundHandler 来处理接收到的 Protobuf 数据,并进行解码。同样,客户端也会设置一个 Bootstrap,连接到服务器,发送和接收 Protobuf 编码的数据。 总的来说,这个项目...

    Unity与Netty通信Demo

    而本Demo中,Unity部分可能使用了名为`TestSocket.unitypackage`的资源包。这个包可能包含了一些预设(Prefabs)、脚本(Scripts)、场景(Scenes)或其他游戏对象,用于演示Unity端如何创建客户端,发送和接收数据...

    UnitySocketProtobuf3Demo-master.zip

    在UnitySocketProtobuf3Demo中,protobuf用于客户端和服务器之间的数据交换格式,简化了数据打包和解析的过程。 5. **网络通信**:客户端和服务器之间的通信是游戏运行的基础,Unity3D通过Socket接口发送protobuf...

    protobuf使用案例

    在GRPC-Demo中,可能包含了以下部分: 1. **Proto文件**:定义服务接口和消息类型,如`service UserService { ... }`。 2. **服务实现**:在服务器端,实现protobuf定义的服务接口,处理客户端请求。 3. **客户端...

    nett权威指南,学习整理的demo代码

    netty学习简单案列demo记录 ...7.netty权威指南中的私有协议栈开发章节,内容包含protocol编解码、心跳、断线重连等。marshalling编解码未走通。 - netty-protocalstack 8.netty+zk实现简单rpc框架 netty-demo-rpc目录

    Mina开发实例(服务端、客户端)DEMO

    在这个"Mina开发实例(服务端、客户端)DEMO"中,我们将深入探讨Mina如何实现长连接通讯。 首先,我们来理解服务端(Server)的实现。在Mina中,服务端通常通过`IoAcceptor`接口来创建,它是监听并接受客户端连接的...

    android protocol buffers demo

    12. **测试和调试**:在开发过程中,可以使用ProtoBuf的工具对消息进行编解码验证,确保数据正确无误地传输。 通过这个“android protocol buffers demo”,开发者可以学习如何在Android项目中引入和使用ProtoBuf,...

    基于Unity3d和Java的聊天室demo,主要功能是实现一个完整的c/s架构,包括编码,解码,消息广播

    【作品名称】:基于Unity3d和Java的聊天室demo,主要...在这个demo中,你可以学到: 1.C#的protobuf序列化和反序列化,基于注解,无需工具 2.Java的protobuf序列化和反序列化,基于注解,无需工具 3.消息体的广播

    grpc java版本demo

    在 "grpc java版本demo" 中,pom.xml 可能包含 GRPC 和 protobuf 的相关依赖,如 `grpc-netty`, `grpc-protobuf`, `grpc-stub` 和 `protobuf-java`。 ```xml &lt;groupId&gt;io.grpc &lt;artifactId&gt;grpc-netty-...

    Android-fpush-基于Nettyprotobuf实现的即时消息推送服务

    在Android应用开发中,即时消息推送服务是必不可少的组件,它能够实现在用户不打开应用的情况下,接收并处理服务器端发送的数据。本项目"Android-fpush-基于Nettyprotobuf实现的即时消息推送服务"就是这样一个解决...

Global site tag (gtag.js) - Google Analytics