测试异常处理

    在图10.4最大帧大小被设置为3个字节。

    上图显示帧的大小被限制为3字节,若输入的字节超过3字节,则超过的字节被丢弃并抛出 TooLongFrameException。在 ChannelPipeline 中的其他ChannelHandler 实现可以处理 TooLongFrameException 或者忽略异常。处理异常在 ChannelHandler.exceptionCaught() 方法中完成,ChannelHandler 提供了一些具体的实现,看下面代码:

    1. 继承 ByteToMessageDecoder 用于解码入站字节到消息
    2. 指定最大需要的帧产生的体积
    3. 如果帧太大就丢弃并抛出一个 TooLongFrameException 异常
    4. 同时从 ByteBuf 读到新帧
    5. 添加帧到解码消息 List

    示例如下:

    1. @Test //1
    2. public void testFramesDecoded() {
    3. ByteBuf buf = Unpooled.buffer(); //2
    4. for (int i = 0; i < 9; i++) {
    5. buf.writeByte(i);
    6. }
    7. ByteBuf input = buf.duplicate();
    8. try {
    9. channel.writeInbound(input.readBytes(4)); //5
    10. Assert.fail(); //6
    11. } catch (TooLongFrameException e) {
    12. // expected
    13. }
    14. Assert.assertTrue(channel.writeInbound(input.readBytes(3))); //7
    15. Assert.assertTrue(channel.finish()); //8
    16. ByteBuf read = (ByteBuf) channel.readInbound();
    17. Assert.assertEquals(buf.readSlice(2), read); //9
    18. read.release();
    19. read = (ByteBuf) channel.readInbound();
    20. Assert.assertEquals(buf.skipBytes(4).readSlice(3), read);
    21. read.release();
    22. buf.release();
    23. }
    1. 使用 @Test 注解
    2. 新建 ByteBuf 写入 9 个字节
    3. 新建 EmbeddedChannel 并安装一个 FixedLengthFrameDecoder 用于测试
    4. 写入 2 个字节并预测生产的新帧(消息)
    5. 写一帧大于帧的最大容量 (3) 并检查一个 TooLongFrameException 异常
    6. 如果异常没有被捕获,测试将失败。注意如果类实现 exceptionCaught() 并且处理了异常 exception,那么这里就不会捕捉异常
    7. 写剩余的 2 个字节预测一个帧
    8. 标记 channel 完成

    即使我们使用 EmbeddedChannel 和 ByteToMessageDecoder。

    应该指出的是,同样的可以做每个 ChannelHandler 的实现,将抛出一个异常。