From 1d6eb6f0ad631effeb61294f2b80f517e7bc1191 Mon Sep 17 00:00:00 2001 From: jrhee17 Date: Mon, 7 Nov 2022 20:04:32 +0900 Subject: [PATCH] Add debug logs for http2 stream errors (#4515) Motivation: We sometimes encounter situations where HTTP/2 header frames are lost due to an exception. Although a RST frame is sent in this case, remotes are still able to send data for the offending stream, which ends up in error logs which armeria doesn't understand. e.g. ``` io.netty.handler.codec.http2.Http2Exception: Stream 1147 does not exist ``` Although normally it might be noisy to be alerted of such failures, it might be useful to view such logs when debugging. Modifications: - Added logging for HTTP/2 `StreamError` - Added logging for connection errors just in case as well. Result: - Easier to debug http2 failure logs. --- .../common/AbstractHttp2ConnectionHandler.java | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/core/src/main/java/com/linecorp/armeria/internal/common/AbstractHttp2ConnectionHandler.java b/core/src/main/java/com/linecorp/armeria/internal/common/AbstractHttp2ConnectionHandler.java index 50fca47015f..f4cd0c32690 100644 --- a/core/src/main/java/com/linecorp/armeria/internal/common/AbstractHttp2ConnectionHandler.java +++ b/core/src/main/java/com/linecorp/armeria/internal/common/AbstractHttp2ConnectionHandler.java @@ -45,6 +45,7 @@ import io.netty.handler.codec.http2.Http2ConnectionEncoder; import io.netty.handler.codec.http2.Http2ConnectionHandler; import io.netty.handler.codec.http2.Http2Exception; +import io.netty.handler.codec.http2.Http2Exception.StreamException; import io.netty.handler.codec.http2.Http2Settings; import io.netty.handler.codec.http2.Http2Stream.State; import io.netty.handler.codec.http2.Http2StreamVisitor; @@ -111,13 +112,20 @@ protected final void onConnectionError(ChannelHandlerContext ctx, boolean outbou handlingConnectionError = true; if (Exceptions.isExpected(cause) || isGoAwaySentException(cause, connection())) { - // Ignore silently. + logger.trace("{} HTTP/2 connection error:", ctx.channel(), cause); } else { logger.warn("{} HTTP/2 connection error:", ctx.channel(), cause); } super.onConnectionError(ctx, outbound, cause, filterHttp2Exception(cause, http2Ex)); } + @Override + protected void onStreamError(ChannelHandlerContext ctx, boolean outbound, Throwable cause, + StreamException http2Ex) { + logger.debug("{} HTTP/2 stream error:", ctx.channel(), cause); + super.onStreamError(ctx, outbound, cause, http2Ex); + } + private static Http2Exception filterHttp2Exception(Throwable cause, @Nullable Http2Exception http2Ex) { if (http2Ex != null) { return http2Ex;