一、本文的目标
- 基于公司一个服务端采用java开发的游戏项目,探索一个合适的服务端热更新[1]方案。
- 讨论java运行时类修改[2]技术。
二、本文范畴内的一些词汇的定义
- 热更新:在不造成用户可感知的中断或响应延迟的前提下完成后端服务迭代更新的过程。
- java运行时类修改:对内存中的class进行任意的改动,包括增加、删除、修改,并且把改动同步到所有受影响class的已创建对象上,后续创建的对象基于最新的class。(目前java是不支持的这种无限制的改动)
三、本文的背景
我现在负责的项目是个h5的rpg游戏,后端是用java写的,登录服主要提供区服的连接入口地址,一个游戏区服对应一个java进程,一个中心服负责处理游戏服之间的消息传递和跨服功能部分逻辑处理。客户端通过登录服获取到游戏服的地址和端口,通过websoclet连接到游戏服上。
主要的业务逻辑在游戏服上,游戏服经常需要更新活动玩法,每次更新需要半小时到一小时的停服更新,会影响玩家的游戏体验。就想探索一个合适的方案实现不停服热更新。
为了对java运行时类修改这块的内容有更多的了解,我列出了相关的可能的实现方案,并整理了一下各个方案的实现原理和优劣势。
项目架构图:
数据层架构图:
四、实现思路
(一)JVM对运行时类修改的支持如何,是否足以实现热更新?
Java 5引入Instrument包,提供了两种方法premain和agentmain实现类的重定义,premain方法可在java命令启动虚拟机时通过-javaagent:指定代理ja。agentmain方法需要JVM提供一个机制,在JVM启动后启动agent。
Java 6引入Attach API机制之后就提供了这么个机制,实现JVM运行时启动agent以及传递类重定义相关的参数。