Netty没有写

Fer*_*big 1 java netty

当尝试使用netty写入时,写入的数据永远不会在远程端结束,并通过Wireshark确认.

我试过了:

//Directly using writeAndFlush
channel.writeAndFlush(new Packet());

//Manually flushing
channel.write(new Packet());
channel.flush();

// Even sending bytes won't work:
channel.writeAndFlush(new byte[]{1,2,3});
Run Code Online (Sandbox Code Playgroud)

当我把它包起来时没有被捕获 try{...}catch(Throwable e){e.printStackTrace();}

我该怎么做来调试这个问题?

Fer*_*big 9

Netty是异步的,这意味着它在写入失败时不会抛出异常.它会返回一个Future<?>在请求完成时更新的异常,而不是抛出异常.确保记录来自此的任何异常作为您的第一个调试步骤:

channel.writeAndFlush(...).addListener(new GenericFutureListener<Future<Object>>() {
    @Override
    public void operationComplete(Future<Object> future) {
        // TODO: Use proper logger in production here
        if (future.isSuccess()) {
            System.out.println("Data written succesfully");
        } else {
            System.out.println("Data failed to write:");
            future.cause().printStackTrace();
        }
    }
});
Run Code Online (Sandbox Code Playgroud)

或者更简单:

channel.writeAndFlush(...).addListener(ChannelFutureListener.FIRE_EXCEPTION_ON_FAILURE);
Run Code Online (Sandbox Code Playgroud)

在得到异常的根本原因后,可能会出现多个问题:

java.lang.UnsupportedOperationException:
unsupported message type: <type> (expected: ...)

注意:使用a时也会抛出ObjectEncoder,但是你的对象没有实现Serializable

默认的Netty频道只能发送ByteBufs和FileRegions.您需要通过向管道添加更多处理程序或将它们手动转换为ByteBufs 来将对象转换为这些类型.

A ByteBuf是字节数组的Netty变体,但具有性能潜力,因为它可以存储在直接存储空间中.

通常使用以下处理程序:

转换String使用a StringEncoder 转换Serializable使用a ObjectEncoder(警告,与普通Java对象流不兼容)转换byte[]使用aByteArrayEncoder

注意:由于TCP是基于流的协议,因此您通常需要附加某种形式的数据包大小,因为您可能无法收到您编写的确切数据包.有关详细信息,请参阅在Netty wiki中处理基于流的传输.