private void write(Channel ch, final Call call) { ch.writeAndFlush(call).addListener(new ChannelFutureListener() { @Override public void operationComplete(ChannelFuture future) throws Exception { // Fail the call if we failed to write it out. This usually because the channel is // closed. This is needed because we may shutdown the channel inside event loop and // there may still be some pending calls in the event loop queue after us. if (!future.isSuccess()) { call.setException(toIOE(future.cause())); } } }); }
@Override public void handlerAdded(ChannelHandlerContext ctx) throws Exception { queue = new CoalescingBufferQueue(ctx.channel()); }
@Override public void channelActive(ChannelHandlerContext ctx) throws Exception { allChannels.add(ctx.channel()); NettyRpcServer.LOG.trace("Connection {}; # active connections={}", ctx.channel().remoteAddress(), (allChannels.size() - 1)); super.channelActive(ctx); }
@Override public void channelInactive(ChannelHandlerContext ctx) throws Exception { allChannels.remove(ctx.channel()); NettyRpcServer.LOG.trace("Disconnection {}; # active connections={}", ctx.channel().remoteAddress(), (allChannels.size() - 1)); super.channelInactive(ctx); }
@Override public void close(ChannelHandlerContext ctx, ChannelPromise promise) throws Exception { if (!queue.isEmpty()) { queue.releaseAndFailAll(new ConnectionClosedException("Connection closed")); } ctx.close(promise); } }
@Override protected synchronized void callTimeout(Call call) { if (channel != null) { channel.pipeline().fireUserEventTriggered(new CallEvent(TIMEOUT, call)); } }
@Override public void channelInactive(ChannelHandlerContext ctx) throws Exception { if (state == State.CLOSED) { return; } failed(ctx.channel(), () -> new IOException("Connection to " + ctx.channel().remoteAddress() + " closed")); }
public void join() { serverChannel.closeFuture().awaitUninterruptibly(); }
@Override public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) { if (msg instanceof Call) { Call call = (Call) msg; id2Call.put(call.id, call); // The call is already in track so here we set the write operation as success. // We will fail the call directly if we can not write it out. promise.trySuccess(); } else { ctx.write(msg, promise); } }
private void shutdown0() { if (channel != null) { channel.close(); channel = null; } }
@Override protected void doRespond(RpcResponse resp) { channel.writeAndFlush(resp); } }
@Override protected void closeInternal() { if (shutdownGroupWhenClose) { group.shutdownGracefully(); } } }
@Override public synchronized InetSocketAddress getListenerAddress() { return ((InetSocketAddress) serverChannel.localAddress()); }
@Override public boolean acceptInboundMessage(Object msg) throws Exception { return super.acceptInboundMessage(msg); }
@Override public boolean isConnectionOpen() { return channel.isOpen(); }
@Override public void handlerAdded(ChannelHandlerContext ctx) throws Exception { queue = new CoalescingBufferQueue(ctx.channel()); }
@Override public void close(ChannelHandlerContext ctx, ChannelPromise promise) throws Exception { if (!queue.isEmpty()) { queue.releaseAndFailAll(new ConnectionClosedException("Connection closed")); } ctx.close(promise); } }
/** * If we have a response, and delay is not set, then respond immediately. Otherwise, do not * respond to client. This is called by the RPC code in the context of the Handler thread. */ @Override public synchronized void sendResponseIfReady() throws IOException { // set param null to reduce memory pressure this.param = null; connection.channel.writeAndFlush(this); } }