Skip to content

Latest commit

 

History

History
218 lines (144 loc) · 5.28 KB

24.心跳.md

File metadata and controls

218 lines (144 loc) · 5.28 KB
title date categories tags description
24.心跳
2020-04-12
Netty
Netty
网络
零拷贝

客户端、服务器需要知道连接是否还正常

读:客户端发消息给Server, Server读

写:Server发消息给客户端,Server写。

即根据数据流动来。

HeartBeat

int a=0;
int b=0;

Netty提供一个IdleStateHandler

Netty 检测空闲状态的处理器

/**
 * Triggers an {@link IdleStateEvent} when a {@link Channel} has not performed
 * read, write, or both operation for a while.
 *
 * <h3>Supported idle states</h3>
 * <table border="1">
 * <tr>
 * <th>Property</th><th>Meaning</th>
 * </tr>
 * <tr>
 * <td>{@code readerIdleTime}</td>
 * <td>an {@link IdleStateEvent} whose state is {@link IdleState#READER_IDLE}
 *     will be triggered when no read was performed for the specified period of
 *     time.  Specify {@code 0} to disable.</td>
 * </tr>
 * <tr>
 * <td>{@code writerIdleTime}</td>
 * <td>an {@link IdleStateEvent} whose state is {@link IdleState#WRITER_IDLE}
 *     will be triggered when no write was performed for the specified period of
 *     time.  Specify {@code 0} to disable.</td>
 * </tr>
 * <tr>
 * <td>{@code allIdleTime}</td>
 * <td>an {@link IdleStateEvent} whose state is {@link IdleState#ALL_IDLE}
 *     will be triggered when neither read nor write was performed for the
 *     specified period of time.  Specify {@code 0} to disable.</td>
 * </tr>
 * </table>
 *
 * <pre>
 * // An example that sends a ping message when there is no outbound traffic
 * // for 30 seconds.  The connection is closed when there is no inbound traffic
 * // for 60 seconds.
 *
 * public class MyChannelInitializer extends {@link ChannelInitializer}&lt;{@link Channel}&gt; {
 *     {@code @Override}
 *     public void initChannel({@link Channel} channel) {
 *         channel.pipeline().addLast("idleStateHandler", new {@link IdleStateHandler}(60, 30, 0));
 *         channel.pipeline().addLast("myHandler", new MyHandler());
 *     }
 * }
 *
 * // Handler should handle the {@link IdleStateEvent} triggered by {@link IdleStateHandler}.
 * public class MyHandler extends {@link ChannelDuplexHandler} {
 *     {@code @Override}
 *     public void userEventTriggered({@link ChannelHandlerContext} ctx, {@link Object} evt) throws {@link Exception} {
 *         if (evt instanceof {@link IdleStateEvent}) {
 *             {@link IdleStateEvent} e = ({@link IdleStateEvent}) evt;
 *             if (e.state() == {@link IdleState}.READER_IDLE) {
 *                 ctx.close();
 *             } else if (e.state() == {@link IdleState}.WRITER_IDLE) {
 *                 ctx.writeAndFlush(new PingMessage());
 *             }
 *         }
 *     }
 * }
 *
 * {@link ServerBootstrap} bootstrap = ...;
 * ...
 * bootstrap.childHandler(new MyChannelInitializer());
 * ...
 * </pre>
 *
 * @see ReadTimeoutHandler
 * @see WriteTimeoutHandler
 */
pipeline.addLast(new IdleStateHandler());
    /**
     * Creates a new instance firing {@link IdleStateEvent}s.
     *
     * @param readerIdleTimeSeconds
     *        an {@link IdleStateEvent} whose state is {@link IdleState#READER_IDLE}
     *        will be triggered when no read was performed for the specified
     *        period of time.  Specify {@code 0} to disable.
     * @param writerIdleTimeSeconds
     *        an {@link IdleStateEvent} whose state is {@link IdleState#WRITER_IDLE}
     *        will be triggered when no write was performed for the specified
     *        period of time.  Specify {@code 0} to disable.
     * @param allIdleTimeSeconds
     *        an {@link IdleStateEvent} whose state is {@link IdleState#ALL_IDLE}
     *        will be triggered when neither read nor write was performed for
     *        the specified period of time.  Specify {@code 0} to disable.
     */
    public IdleStateHandler(
            int readerIdleTimeSeconds,
            int writerIdleTimeSeconds,
            int allIdleTimeSeconds) {

        this(readerIdleTimeSeconds, writerIdleTimeSeconds, allIdleTimeSeconds,
             TimeUnit.SECONDS);
    }

readerIdleTimeSeconds 多久没读

当 多久内未执行任何读取时,将触发状态为 READER_IDLE(读空闲) 的 IdleStateEvent 事件

writerIdleTimeSeconds 多久没写

当多久时间内未执行任何写操作时,将触发一个状态为 WRITER_IDLE(写空闲) 的 事件

allIdleTimeSeconds 多久没有读写

有了handlerRemoved回调方法, 为什么还要心跳检测?

很多时候,连接断了,服务器是无法感知的。比如飞行状态,直接关机,直接断网。

当触发了空闲事件(IdleStateEvent)后,会将事件传递到Pipeline的下一个Handler处理(传入到下一个Handler的userEventTigger方法)因此需要在userEventTigger方法加入对空闲检测的自定义处理。

https://blog.csdn.net/z69183787/article/details/52980724

https://blog.csdn.net/z69183787/article/details/52980768

https://blog.csdn.net/z69183787/article/details/52980813

http://www.tianshouzhi.com/api/tutorials/netty/344

建立连接

handlerAdded channelRegistered channelActive

从服务端直接移除连接,

channelInactive channelUnregistered handlerRemoved

服务器挂了

channelInactive channelUnregistered handlerRemoved