赞
踩
前面介绍了Netty服务端客户端基本通信框架的搭建过程。下面将介绍Netty如何进行心跳检测以及处理客户端的断线重连。
为了适应恶劣的网络环境,比如网络超时、闪断,客户端进程僵死,需要机制来保证双方的通信能正常工作或者自动恢复。对于服务端来说,当客户端由于某些原因导致无法与服务端通信的,服务端需要主动注销与客户端的连接,减少无效链接的资源消耗。对于客户端来说,当服务进程宕机后进行重启,客户端应该自动能发起重连操作。
(一)心跳监测客户端
采用心跳机制,来确保服务端能及时发现无效的客户端链接。这里有个问题,心跳机制的发起方应该由服务端还是客户端。假设服务端出现宕机,客户端唯一能做的就是保证能及时发现服务端重启后能进行重连。因此,可以只由服务端来发起心跳检测。一旦服务端发现客户端连接超时多次,则 立即关闭链路。
心跳检测具体的设计思路如下:
1.服务端定时查看客户端链路是否空闲,一旦持续时间T没有收到客户端的请求包,则主动发送Ping包给客户端,同时心跳超时次数加1。
2.客户端收到服务的Ping请求,则立即发送一个Pong应答包。
3.服务端每次收到客户端的数据包,则重置超时次数。若连续N次未收到心跳应答包,则关闭链接。
心跳检测示例代码如下:
1.服务端NettyChatServer类的ChannelPipeline增加空闲状态处理器(IdleStateHandler)。该类用于检测通信Channel的读写状态超时,以此来实现心跳检测。IdleStateHandler的构造函数有三个参数,依次为读超时秒数,写超时秒数,读写超时秒数。我们只需要用到第一个参数。
2.ChatServerHandler类必须覆写userEventTriggered()方法处理超时逻辑。当超时次数少于指定次数时,向客户端发送Ping包;当超时次数大于指定次数时,注销客户端链接。
[java] view plain copy
3.增加下发包ClientHeartBeat类定义。客户端在收到该包的时候,需要向服务端发送一个应答包。
[java] view plain copy
4.服务端在收到应答包后,重置超时次数为0
心跳调试技巧:如果需要演示心跳超时,只需在客户端启动后在任意代码里加个断点,这样服务端就会检测到客户端读超时。
(二)客户端断线重连
当服务端宕机后,客户端需要定时检测服务端开启状态,重新连接。实现逻辑也比较简单,只要在NettyChatClient类断开链接的逻辑后加上重连逻辑即可(reConnectServer()方法)。每次重连检测不必过于频繁,可以让线程休眠一段时间。
[java] view plain copy
调试技巧:启动服务端与客户端后,单方面关闭服务端,即可看见客户端定时重连了。需要保证客户端重连成功后,能够与服务端收发数据,同时客户端也不无须继续检测重连。
全部代码已在github上托管(代码经过多次重构,与博客上的代码略有不同)
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。