刚开始对这个方法不是很清楚,执行ctx.writeAndFlush()方法时,是写完后立即执行flush,还是同样会将写事件传给下一个handelr。等执行完所有的handler的write方法后再flush()。
接着跟着源码走一遍。
第一步
@Override
protected void channelRead0(ChannelHandlerContext ctx, ByteBuf msg) throws Exception {
ByteBuf in = (ByteBuf) msg;
System.out.println("server received:" + in.toString(CharsetUtil.UTF_8));
//ctx.write(Unpooled.wrappedBuffer(ByteBufUtil.decodeHexDump("aa")));
//ctx.channel().write(Unpooled.wrappedBuffer(ByteBufUtil.decodeHexDump("aa")));
//执行writeAndFlush()方法
ctx.writeAndFlush(Unpooled.wrappedBuffer(ByteBufUtil.decodeHexDump("aa")));
}
第二步
private void write(Object msg, boolean flush, ChannelPromise promise) {
AbstractChannelHandlerContext next = findContextOutbound();
final Object m = pipeline.touch(msg, next);
EventExecutor executor = next.executor();
if (executor.inEventLoop()) {
if (flush) {
//执行到这一步,next就是下一个handler
next.invokeWriteAndFlush(m, promise);
} else {
next.invokeWrite(m, promise);
}
} else {
AbstractWriteTask task;
if (flush) {
task = WriteAndFlushTask.newInstance(next, m, promise);
} else {
task = WriteTask.newInstance(next, m, promise);
}
safeExecute(executor, task, promise, m);
}
}
第三步
// write方法和flush方法分开执行。接着看 invokeWrite0(msg, promise);
private void invokeWriteAndFlush(Object msg, ChannelPromise promise) {
if (invokeHandler()) {
invokeWrite0(msg, promise);
invokeFlush0();
} else {
writeAndFlush(msg, promise);
}
}
第四步
private void invokeWrite0(Object msg, ChannelPromise promise) {
try {
//直接调用下一个handler的write方法,
//到这为止我们可以确认了会执行完所有的handler的write方法再flush
((ChannelOutboundHandler) handler()).write(this, msg, promise);
} catch (Throwable t) {
notifyOutboundHandlerException(t, promise);
}
}
总结:执行ctx.writeAndFlush()方法。会将写事件传给下一个handelr。等执行完所有的handler的write方法后再flush()。