Netty断线重连

文章作者:jqpeng
原文链接: Netty断线重连

Netty断线重连

最近使用Netty开发一个中转服务,需要一直保持与Server端的连接,网络中断后需要可以自动重连,查询官网资料,实现方案很简单,核心思想是在channelUnregistered钩子函数里执行重连。

创建连接

需要把configureBootstrap重构为一个函数,方便后续复用

  1. EventLoopGroup group = new NioEventLoopGroup(); 

  1. private volatile Bootstrap bootstrap; 


  1. public void init(String host, int port) throws RobotException { 

  1. this.serverIp = host; 

  1. this.serverPort = port; 

  1. try { 

  1. // 创建并初始化 Netty 客户端 Bootstrap 对象 

  1. bootstrap = configureBootstrap(new Bootstrap(),group); 

  1. bootstrap.option(ChannelOption.TCP_NODELAY, true); 

  1. doConnect(bootstrap); 


  1. catch(Exception ex){ 

  1. ex.printStackTrace(); 

  1. throw new RobotException(“connect remote control server error!”,ex.getCause()); 




  1. Bootstrap configureBootstrap(Bootstrap b, EventLoopGroup g) { 

  1. b.group(g).channel(NioSocketChannel.class) 

  1. .remoteAddress(serverIp, serverPort) 

  1. .handler(new ChannelInitializer<SocketChannel>() { 

  1. @Override 

  1. public void initChannel(SocketChannel channel) throws Exception { 

  1. ChannelPipeline pipeline = channel.pipeline(); 

  1. // 编解码器 

  1. pipeline.addLast(protoCodec); 

  1. // 请求处理 

  1. pipeline.addLast(RobotClient.this); 


  1. }); 


  1. return b; 



  1. void doConnect(Bootstrap b) { 

  1. try { 


  1. ChannelFuture future = b.connect(); 

  1. future.addListener(new ChannelFutureListener() { 

  1. @Override 

  1. public void operationComplete(ChannelFuture future) throws Exception { 

  1. if (future.isSuccess()) { 

  1. System.out.println(“Started Tcp Client: “ + serverIp); 

  1. } else { 

  1. System.out.println(“Started Tcp Client Failed: “); 


  1. if (future.cause() != null) { 

  1. future.cause().printStackTrace(); 




  1. }); 

  1. } catch (Exception e) { 

  1. e.printStackTrace(); 



断线重连

来看断线重连的关键代码:

  1. @ChannelHandler.Sharable 

  1. public class RobotClient extends SimpleChannelInboundHandler<RobotProto> { 

  1. @Override 

  1. public void channelUnregistered(ChannelHandlerContext ctx) throws Exception { 

  1. // 状态重置 

  1. isConnected = false; 

  1. this.serverStatus = -1; 


  1. final EventLoop loop = ctx.channel().eventLoop(); 

  1. loop.schedule(new Runnable() { 

  1. @Override 

  1. public void run() { 

  1. doConnect(configureBootstrap(new Bootstrap(), loop)); 


  1. }, 1, TimeUnit.SECONDS); 



需要注意,Client类需要添加@ChannelHandler.Sharable注解,否则重连时会报错


作者:Jadepeng
出处:jqpeng的技术记事本–http://www.cnblogs.com/xiaoqi
您的支持是对博主最大的鼓励,感谢您的认真阅读。
本文版权归作者所有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。