<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ThinkChat2.0新版上線,更智能更精彩,支持會話、畫圖、視頻、閱讀、搜索等,送10W Token,即刻開啟你的AI之旅 廣告
                本節,將使用 EmbeddedChannel 來測試 ChannelHandler ### [](https://github.com/waylau/essential-netty-in-action/blob/master/NETTY%20BY%20EXAMPLE/Testing%20ChannelHandler.md#測試入站消息)測試入站消息 我們來編寫一個簡單的 ByteToMessageDecoder 實現,有足夠的數據可以讀取時將產生固定大小的包,如果沒有足夠的數據可以讀取,則會等待下一個數據塊并再次檢查是否可以產生一個完整包。 如圖所示,它可能會占用一個以上的“event”以獲取足夠的字節產生一個數據包,并將它傳遞到 ChannelPipeline 中的下一個 ChannelHandler, [![](https://box.kancloud.cn/2015-08-19_55d478b067ad7.jpg)](https://github.com/waylau/essential-netty-in-action/blob/master/images/Figure%2010.2%20Decoding%20via%20FixedLengthFrameDecoder.jpg) Figure 10.2 Decoding via FixedLengthFrameDecoder 實現如下: Listing 10.1 FixedLengthFrameDecoder implementation ~~~ public class FixedLengthFrameDecoder extends ByteToMessageDecoder { //1 private final int frameLength; public FixedLengthFrameDecoder(int frameLength) { //2 if (frameLength <= 0) { throw new IllegalArgumentException( "frameLength must be a positive integer: " + frameLength); } this.frameLength = frameLength; } @Override protected void decode(ChannelHandlerContext ctx, ByteBuf in, List<Object> out) throws Exception { if (in.readableBytes() >= frameLength) { //3 ByteBuf buf = in.readBytes(frameLength);//4 out.add(buf); //5 } } } ~~~ 1. 繼承 ByteToMessageDecoder 用來處理入站的字節并將他們解碼為消息 2. 指定產出的幀的長度 3. 檢查是否有足夠的字節用于讀到下個幀 4. 從 ByteBuf 讀取新幀 5. 添加幀到解碼好的消息 List 下面是單元測試的例子,使用 EmbeddedChannel Listing 10.2 Test the FixedLengthFrameDecoder ~~~ public class FixedLengthFrameDecoderTest { @Test //1 public void testFramesDecoded() { ByteBuf buf = Unpooled.buffer(); //2 for (int i = 0; i < 9; i++) { buf.writeByte(i); } ByteBuf input = buf.duplicate(); EmbeddedChannel channel = new EmbeddedChannel(new FixedLengthFrameDecoder(3)); //3 Assert.assertFalse(channel.writeInbound(input.readBytes(2))); //4 Assert.assertTrue(channel.writeInbound(input.readBytes(7))); Assert.assertTrue(channel.finish()); //5 ByteBuf read = (ByteBuf) channel.readInbound(); Assert.assertEquals(buf.readSlice(3), read); read.release(); read = (ByteBuf) channel.readInbound(); Assert.assertEquals(buf.readSlice(3), read); read.release(); read = (ByteBuf) channel.readInbound(); Assert.assertEquals(buf.readSlice(3), read); read.release(); Assert.assertNull(channel.readInbound()); buf.release(); } @Test public void testFramesDecoded2() { ByteBuf buf = Unpooled.buffer(); for (int i = 0; i < 9; i++) { buf.writeByte(i); } ByteBuf input = buf.duplicate(); EmbeddedChannel channel = new EmbeddedChannel(new FixedLengthFrameDecoder(3)); Assert.assertFalse(channel.writeInbound(input.readBytes(2))); Assert.assertTrue(channel.writeInbound(input.readBytes(7))); Assert.assertTrue(channel.finish()); ByteBuf read = (ByteBuf) channel.readInbound(); Assert.assertEquals(buf.readSlice(3), read); read.release(); read = (ByteBuf) channel.readInbound(); Assert.assertEquals(buf.readSlice(3), read); read.release(); read = (ByteBuf) channel.readInbound(); Assert.assertEquals(buf.readSlice(3), read); read.release(); Assert.assertNull(channel.readInbound()); buf.release(); } } ~~~ 1. 測試增加 @Test 注解 2. 新建 ByteBuf 并用字節填充它 3. 新增 EmbeddedChannel 并添加 FixedLengthFrameDecoder 用于測試 4. 寫數據到 EmbeddedChannel 5. 標記 channel 已經完成 6. 讀產生的消息并且校驗 如上面代碼,testFramesDecoded() 方法想測試一個 ByteBuf,這個ByteBuf 包含9個可讀字節,被解碼成包含了3個可讀字節的 ByteBuf。你可能注意到,它寫入9字節到通道是通過調用 writeInbound() 方法,之后再執行 finish() 來將 EmbeddedChannel 標記為已完成,最后調用readInbound() 方法來獲取 EmbeddedChannel 中的數據,直到沒有可讀字節。testFramesDecoded2() 方法采取同樣的方式,但有一個區別就是入站ByteBuf分兩步寫的,當調用 writeInbound(input.readBytes(2)) 后返回 false 時,FixedLengthFrameDecoder 值會產生輸出,至少有3個字節是可讀,testFramesDecoded2() 測試的工作相當于testFramesDecoded()。 ### [](https://github.com/waylau/essential-netty-in-action/blob/master/NETTY%20BY%20EXAMPLE/Testing%20ChannelHandler.md#testing-outbound-messages)Testing outbound messages 測試的處理出站消息類似于我們剛才看到的一切。這個例子將使用的實現MessageToMessageEncoder:AbsIntegerEncoder。 * 當收到 flush() 它將從 ByteBuf 讀取4字節整數并給每個執行Math.abs()。 * 每個整數接著寫入 ChannelHandlerPipeline 圖10.3顯示了邏輯。 [![](https://box.kancloud.cn/2015-08-19_55d478b5a5580.jpg)](https://github.com/waylau/essential-netty-in-action/blob/master/images/10.3%20Encoding%20via%20AbsIntegerEncoder.jpg) Figure 10.3 Encoding via AbsIntegerEncoder 示例如下: Listing 10.3 AbsIntegerEncoder ~~~ public class AbsIntegerEncoder extends MessageToMessageEncoder<ByteBuf> { //1 @Override protected void encode(ChannelHandlerContext channelHandlerContext, ByteBuf in, List<Object> out) throws Exception { while (in.readableBytes() >= 4) { //2 int value = Math.abs(in.readInt());//3 out.add(value); //4 } } } ~~~ 1. 繼承 MessageToMessageEncoder 用于編碼消息到另外一種格式 2. 檢查是否有足夠的字節用于編碼 3. 讀取下一個輸入 ByteBuf 產出的 int 值,并計算絕對值 4. 寫 int 到編碼的消息 List 在前面的示例中,我們將使用 EmbeddedChannel 測試代碼。清單10.4 Listing 10.4 Test the AbsIntegerEncoder ~~~ public class AbsIntegerEncoderTest { @Test //1 public void testEncoded() { ByteBuf buf = Unpooled.buffer(); //2 for (int i = 1; i < 10; i++) { buf.writeInt(i * -1); } EmbeddedChannel channel = new EmbeddedChannel(new AbsIntegerEncoder()); //3 Assert.assertTrue(channel.writeOutbound(buf)); //4 Assert.assertTrue(channel.finish()); //5 for (int i = 1; i < 10; i++) { Assert.assertEquals(i, channel.readOutbound()); //6 } Assert.assertNull(channel.readOutbound()); } } ~~~ 1. 用 @Test 標記 2. 新建 ByteBuf 并寫入負整數 3. 新建 EmbeddedChannel 并安裝 AbsIntegerEncoder 來測試 4. 寫 ByteBuf 并預測 readOutbound() 產生的數據 5. 標記 channel 已經完成 6. 讀取產生到的消息,檢查負值已經編碼為絕對值
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看