Netty 3.5.3 を使用して、要求応答通信なしで継続的に小さなデータ パケットを送信する必要がある UDP サーバーを実装しています。フォーラムのどこでも、SimpleChannelHandler の channelBound メソッドをオーバーライドするのが最適なフックであるというヒントを見つけました。
private static class MyHandler extends SimpleChannelHandler {
private TargetDataReader dataReader = new TargetDataReader();
private InetSocketAddress remoteAddress;
private long sleep;
/**
* @param host
* @param port
*/
public MyHandler(String host, int port, long sleep) {
super();
this.remoteAddress = new InetSocketAddress(host, port);
this.sleep = sleep;
}
/*
* {@inheritDoc}
*/
@Override
public void channelBound(ChannelHandlerContext ctx, ChannelStateEvent e) throws Exception {
Channel ch = e.getChannel();
int cnt = 0;
long start = System.currentTimeMillis();
byte[] targetData;
while ((targetData = dataReader.nextData()) != null) {
ChannelBuffer tdBuf = ChannelBuffers.wrappedBuffer(targetData);
++cnt;
ChannelFuture cf = ch.write(tdBuf, this.remoteAddress);
cf.addListener(new ChannelFutureListener() {
@Override
public void operationComplete(ChannelFuture future) throws Exception {
System.out.println("Server - record sent "
+ (future.isSuccess() ? "successfully" : "failed"));
}
});
cf.await(30);
if (sleep > 0)
Thread.sleep(sleep);
System.out.println("Server - written records " + cnt);
}
long duration = System.currentTimeMillis() - start;
System.out.println("Server - duration=" + duration + ", cnt=" + cnt + ", records/sec="
+ String.format("%f", ((double) cnt) / duration * 1000));
}
一見、うまくいくように見えました。しかし、さらに詳しく調べてみると、受信クライアントがデータ パケットの約 50% しか受け取っていないことがわかりました。さらに、それが実際の問題だと思いますが、ChannelFuture cf = ch.write(tdBuf, this.remoteAddress);を呼び出すときに、サーバーは実際にはデータパケットを送信しません。ただし、channelBound メソッドが終了するまでは、1 回のストロークではありません。残念ながら、私にはわかりません。ヒントをいただければ幸いです。