使用netty进行客户端网络编程及断线重连功能实现

本文主要是介绍使用netty进行客户端网络编程及断线重连功能实现,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

       不管做哪个方向开发,都会有那么一两个牛B闪闪的库,可以极大的方便开发,比如java网络编程中的netty库。无论客户端还是服务端网络编程,netty基本都是首选网络库,健壮、高效、稳定,并且已经得到很多商业项目验证。

       当用netty进行客户端网络编程时,与服务端建立连接并完成数据编码、解码、通信是最基础功能,考虑程序的健壮性,则断线重连是必不可少的一个功能点。netty源码的example文件夹中uptime目录中有相关示例demo,但是总觉得该样例代码封装的不够好,于是决定自己动手重新写一个,如果有更优雅的断线重连实现方法,希望大家将链接留言发我。下面是主体代码,Handler部分就不分享了。

public class BaseClient implements Runnable {private static Logger LOGGER = LoggerTools.getInstance(BaseClient.class);private String host_;private int port_;private int reConnectCount_ = 0;private ClientHandler clientHandler_;private OnMessageListener messageListener_;private OnStartupListener startupListener_;private volatile boolean isChannelPrepared_;private final static int MAX_MESSAGE_LENGTH = 8192;public BaseClient(String host, int port, OnMessageListener messageListener, OnStartupListener startupListener) {host_ = host;port_ = port;messageListener_ = messageListener;startupListener_ = startupListener;}@Overridepublic void run() {connect(host_, port_);}// 发送消息public void sendMessage(String msg, ResultListener<String> listener) {if (isChannelPrepared_) {clientHandler_.sendMessage(msg, listener);} else {listener.onFailure(msg);LOGGER.error("连接还未建立, 无法发送数据...");}}// 建立连接private void connect(String host, int port) {EventLoopGroup group = new NioEventLoopGroup();try {Bootstrap b = new Bootstrap();b.group(group);b.channel(NioSocketChannel.class);b.option(ChannelOption.TCP_NODELAY, true);b.handler(new ChannelInitializer<SocketChannel>() {@Overrideprotected void initChannel(SocketChannel ch) throws Exception {ChannelPipeline p = ch.pipeline();p.addLast(new LengthFieldBasedFrameDecoder(MAX_MESSAGE_LENGTH, 0, 4, 0 ,4));p.addLast(new LengthFieldPrepender(4));p.addLast(new StringDecoder(CharsetUtil.UTF_8));p.addLast(new StringEncoder(CharsetUtil.UTF_8));clientHandler_ = new ClientHandler(messageListener_);p.addLast(clientHandler_);}});ChannelFuture f = b.connect(host, port).sync();f.addListener(new GenericFutureListener<Future<? super Void>>() {@Overridepublic void operationComplete(Future<? super Void> future) throws Exception {if (future.isSuccess()) {reConnectCount_ = 0;isChannelPrepared_ = true;startupListener_.onCompletion(true);LOGGER.info("与服务器{}:{}连接建立成功...", host_, port_);} else {isChannelPrepared_ = false;startupListener_.onCompletion(false);LOGGER.info("与服务器{}:{}连接建立失败...", host_, port_);}}});f.channel().closeFuture().sync();} catch (Exception e) {isChannelPrepared_ = false;LOGGER.error("与服务器{}:{}连接出现异常...", host_, port_);} finally {isChannelPrepared_ = false;group.shutdownGracefully();reConnect(host, port);}}// 断线重连private void reConnect(String host, int port) {// fixme: 重连显式退出?try {isChannelPrepared_ = false;int delay = ++reConnectCount_ * 5;reConnectCount_ = reConnectCount_ > 23 ? 23 : reConnectCount_;LOGGER.error("与服务器{}:{}连接已断开, {}秒后重连...", host, port, delay);Thread.sleep(delay * 1000);connect(host, port);} catch (Exception e) {e.printStackTrace();}}}


这篇关于使用netty进行客户端网络编程及断线重连功能实现的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1114976

相关文章

SpringBoot结合Docker进行容器化处理指南

《SpringBoot结合Docker进行容器化处理指南》在当今快速发展的软件工程领域,SpringBoot和Docker已经成为现代Java开发者的必备工具,本文将深入讲解如何将一个SpringBo... 目录前言一、为什么选择 Spring Bootjavascript + docker1. 快速部署与

深入理解Go语言中二维切片的使用

《深入理解Go语言中二维切片的使用》本文深入讲解了Go语言中二维切片的概念与应用,用于表示矩阵、表格等二维数据结构,文中通过示例代码介绍的非常详细,需要的朋友们下面随着小编来一起学习学习吧... 目录引言二维切片的基本概念定义创建二维切片二维切片的操作访问元素修改元素遍历二维切片二维切片的动态调整追加行动态

Linux下删除乱码文件和目录的实现方式

《Linux下删除乱码文件和目录的实现方式》:本文主要介绍Linux下删除乱码文件和目录的实现方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录linux下删除乱码文件和目录方法1方法2总结Linux下删除乱码文件和目录方法1使用ls -i命令找到文件或目录

prometheus如何使用pushgateway监控网路丢包

《prometheus如何使用pushgateway监控网路丢包》:本文主要介绍prometheus如何使用pushgateway监控网路丢包问题,具有很好的参考价值,希望对大家有所帮助,如有错误... 目录监控网路丢包脚本数据图表总结监控网路丢包脚本[root@gtcq-gt-monitor-prome

SpringBoot+EasyExcel实现自定义复杂样式导入导出

《SpringBoot+EasyExcel实现自定义复杂样式导入导出》这篇文章主要为大家详细介绍了SpringBoot如何结果EasyExcel实现自定义复杂样式导入导出功能,文中的示例代码讲解详细,... 目录安装处理自定义导出复杂场景1、列不固定,动态列2、动态下拉3、自定义锁定行/列,添加密码4、合并

mybatis执行insert返回id实现详解

《mybatis执行insert返回id实现详解》MyBatis插入操作默认返回受影响行数,需通过useGeneratedKeys+keyProperty或selectKey获取主键ID,确保主键为自... 目录 两种方式获取自增 ID:1. ​​useGeneratedKeys+keyProperty(推

Spring Boot集成Druid实现数据源管理与监控的详细步骤

《SpringBoot集成Druid实现数据源管理与监控的详细步骤》本文介绍如何在SpringBoot项目中集成Druid数据库连接池,包括环境搭建、Maven依赖配置、SpringBoot配置文件... 目录1. 引言1.1 环境准备1.2 Druid介绍2. 配置Druid连接池3. 查看Druid监控

Python通用唯一标识符模块uuid使用案例详解

《Python通用唯一标识符模块uuid使用案例详解》Pythonuuid模块用于生成128位全局唯一标识符,支持UUID1-5版本,适用于分布式系统、数据库主键等场景,需注意隐私、碰撞概率及存储优... 目录简介核心功能1. UUID版本2. UUID属性3. 命名空间使用场景1. 生成唯一标识符2. 数

Linux在线解压jar包的实现方式

《Linux在线解压jar包的实现方式》:本文主要介绍Linux在线解压jar包的实现方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录linux在线解压jar包解压 jar包的步骤总结Linux在线解压jar包在 Centos 中解压 jar 包可以使用 u

linux解压缩 xxx.jar文件进行内部操作过程

《linux解压缩xxx.jar文件进行内部操作过程》:本文主要介绍linux解压缩xxx.jar文件进行内部操作,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录一、解压文件二、压缩文件总结一、解压文件1、把 xxx.jar 文件放在服务器上,并进入当前目录#