Netty存在心跳检测机制,当客户端的连接超过一定时间没有读,或者写的时候,服务端可以检测出来并提示
IdleStateHandler 是netty处理空闲状态的处理器
具体实现步骤为:
1.readerIdleTime : 表示多长时间没有读,就会发送一个心跳检测包检测是否连接
2.writerIdleTime : 表示多长时间没有写,就会发送一个心跳检测包检测是否连接
3.allIdleTime : 表示多长时间没有读和写,就会发送一个心跳检测包检测是否连接
4.当有空闲的时候,就会触发 IdleStateEvent 事件
5.当IdleStateEvent触发后,就会传递给管道的下一个handler去处理,通过回调触发,下一个handler的userEventTiggered,在该方法中去处理当IdleStateEvent(读空闲,写空闲,读写空闲)
实现服务端的代码:
package com.jym.heart;
import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.*;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import io.netty.handler.logging.LogLevel;
import io.netty.handler.logging.LoggingHandler;
import io.netty.handler.timeout.IdleStateHandler;
import java.util.concurrent.TimeUnit;
/**
* @program: NettyPro
* @description: 心跳检测
* @author: jym
* @create: 2020/02/10
*/
public class JymHeartServer {
public static void main(String[] args) throws InterruptedException {
EventLoopGroup bossGroup = new NioEventLoopGroup();
EventLoopGroup workerGroup = new NioEventLoopGroup();
try {
ServerBootstrap serverBootstrap = new ServerBootstrap();
serverBootstrap.group(bossGroup,workerGroup).channel(NioServerSocketChannel.class)
// 在bossGroup增加日志处理器
.handler(new LoggingHandler(LogLevel.INFO))
.option(ChannelOption.SO_BACKLOG,128)
.childOption(ChannelOption.SO_KEEPALIVE,true)
.childHandler(new ChannelInitializer<SocketChannel>() {
@Override
protected void initChannel(SocketChannel socketChannel) throws Exception {
ChannelPipeline pipeline = socketChannel.pipeline();
// 加入netty提供的 IdleStateHandler
/**
IdleStateHandler 是netty处理空闲状态的处理器
1.readerIdleTime : 表示多长时间没有读,就会发送一个心跳检测包检测是否连接
2.writerIdleTime : 表示多长时间没有写,就会发送一个心跳检测包检测是否连接
3.allIdleTime : 表示多长时间没有读和写,就会发送一个心跳检测包检测是否连接
4.当有空闲的时候,就会触发 IdleStateEvent 事件
5.当IdleStateEvent触发后,就会传递给管道的下一个handler去处理,
通过回调触发,下一个handler的userEventTiggered,在该方法中去处理当IdleStateEvent(读空闲,写空闲,读写空闲)
*/
pipeline.addLast(new IdleStateHandler(3,5,7, TimeUnit.SECONDS));
// 加入一个对空闲检测进一步处理的自定义handler
pipeline.addLast(new JymHeartServerHandler());
}
});
System.out.println("服务器已启动");
ChannelFuture sync = serverBootstrap.bind(9000).sync();
sync.channel().closeFuture().sync();
} finally {
bossGroup.shutdownGracefully();
workerGroup.shutdownGracefully();
}
}
}
自定义处理器:
package com.jym.heart;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import io.netty.handler.timeout.IdleStateEvent;
/**
* @program: NettyPro
* @description:
* @author: jym
* @create: 2020/02/10
*/
public class JymHeartServerHandler extends ChannelInboundHandlerAdapter {
/**
*
* @param ctx 上下文
* @param evt 事件
*/
@Override
public void userEventTriggered(ChannelHandlerContext ctx, Object evt) throws Exception {
if(evt instanceof IdleStateEvent){
// 将evt 向下转型 IdleStateEvent
IdleStateEvent event = (IdleStateEvent)evt;
String eventType = null;
switch (event.state()) {
case ALL_IDLE:
eventType = "读空闲";
break;
case READER_IDLE:
eventType = "写空闲";
break;
case WRITER_IDLE:
eventType = "读写空闲";
break;
}
System.out.println(ctx.channel().remoteAddress()+"----超时事件发生----"+eventType);
}
}
}
学习年限不足,知识过浅,说的不对请见谅。
世界上有10种人,一种是懂二进制的,一种是不懂二进制的。
来源:CSDN
作者:jym12138
链接:https://blog.csdn.net/weixin_43326401/article/details/104258789