我有一个使用Java Netty 4.0的简单客户端服务器。问题是我不知道为什么Netty Server无法看到从Netty客户端发送的消息,该消息长于16KB。我尝试输入较短的消息,服务器可以读取它。
Netty客户的代码
class ClientCommunicator {
public void sendMessage() {
Bootstrap bootstrap = new Bootstrap();
bootstrap.group(group)
.channel(NioSocketChannel.class)
.option(ChannelOption.TCP_NODELAY, true)
.handler(new ChannelInitializer<SocketChannel>() {
@Override
public void initChannel(SocketChannel ch) throws Exception {
ch.pipeline().addLast(
new LoggingHandler(LogLevel.INFO),
new DelimiterBasedFrameDecoder(Integer.MAX_VALUE, Delimiters.lineDelimiter()),
new StringEncoder(),
new StringDecoder(),
new ClientCommunicatorHandler(message));
}
});
// Start the connection attempt.
log.info("##### SENDING TO HOST: " + this.host + " and POST " + this.port);
bootstrap.connect(this.host, this.port).sync().channel().closeFuture().sync();
log.debug("##### Message sent successfully. (!)");
}
}
class ClientCommunicatorHandler extends SimpleChannelInboundHandler<String> {
private final Message inboxMessage;
ClientCommunicatorHandler(@NotNull Message message) {
this.inboxMessage = message;
}
@Override
public void channelActive(ChannelHandlerContext ctx) throws Exception {
String message = RasFedStatusMessageHandler.RASFED_IDENTIFIER +
this.inboxMessage.toSerializedString().replace("\n", "").replace("\r", "") + "\n";
log.debug("#### Sending message: {}", message.substring(0, 200));
ctx.writeAndFlush(message);
ctx.close();
}
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
log.error("Error caught in client communication service: ", cause);
ctx.close();
}
@Override
protected void channelRead0(ChannelHandlerContext ctx, String msg) throws Exception {
log.info("#### What I'm doing here?");
}
}
Netty Server从客户端接收消息的代码
public class ServerCommunicator {
private final int port;
public ServerCommunicator(int port) {
this.port = port;
}
public void run(final LocalNode localNode, final InpeerNodeRegistry inpeerNodeRegistry, final OutpeerNodeRegistry outpeerNodeRegistry) throws Exception {
// Configure the server.
EventLoopGroup bossGroup = new NioEventLoopGroup();
EventLoopGroup workerGroup = new NioEventLoopGroup();
try {
ServerBootstrap serverBootstrap = new ServerBootstrap();
serverBootstrap.group(bossGroup, workerGroup)
.channel(NioServerSocketChannel.class)
.handler(new LoggingHandler(LogLevel.TRACE))
.childHandler(new ChannelInitializer<SocketChannel>() {
@Override
public void initChannel(SocketChannel ch) throws Exception {
ch.pipeline().addLast(
new LoggingHandler(LogLevel.TRACE),
new DelimiterBasedFrameDecoder(Integer.MAX_VALUE, Delimiters.lineDelimiter()),
new NettyObjectEncode(),
new StringDecoder(),
new ServerCommunicatorHandler(localNode, inpeerNodeRegistry, outpeerNodeRegistry));
}
});
// Start the server.
ChannelFuture channelFuture = serverBootstrap.bind(port).sync();
// Wait until the server socket is closed.
channelFuture.channel().closeFuture().sync();
} finally {
// Shut down all event loops to terminate all threads.
bossGroup.shutdownGracefully();
workerGroup.shutdownGracefully();
}
}
}
class NettyObjectEncode extends MessageToByteEncoder<ByteArrayResponse> {
private final Logger log = LoggerFactory.getLogger(NettyObjectEncode.class);
@Override
protected void encode(ChannelHandlerContext chc, ByteArrayResponse byteArrayResponse, ByteBuf bb) throws Exception {
byte[] bytes = byteArrayResponse.getDatas();
String data = new String(bytes);
if (data.contains("bigdata")) {
log.info("#### Received Message: " + data);
}
bb.writeBytes(bytes);
}
}
// Server handlers
class ServerCommunicatorHandler extends SimpleChannelInboundHandler<String> {
@Override
protected void channelRead0(ChannelHandlerContext ctx, String message) throws Exception {
InetSocketAddress address = (InetSocketAddress) ctx.channel().remoteAddress();
MessageContainer messageContainer = new MessageContainer(message, address);
log.debug("\n");
// Handle received message and write result back to the sender
Object response = this.handleMessage(messageContainer);
if (response instanceof String) {
ctx.channel().pipeline().remove(NettyObjectEncode.class);
ctx.channel().pipeline().addFirst(new StringEncoder());
}
if (response != null) {
ctx.write(response);
ctx.flush();
}
ctx.close();
}
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
log.error("Error caught in server communication service: ", cause);
ctx.close();
}
}