This is an automated email from the ASF dual-hosted git repository. Cole-Greer pushed a commit to branch java-streaming-no-server in repository https://gitbox.apache.org/repos/asf/tinkerpop.git
commit 080d6427246cc841e9f23f25ff6481d155f36180 Author: Cole Greer <[email protected]> AuthorDate: Tue May 12 11:48:41 2026 -0700 revert server guard against multiple LastHttpContent responses --- .../gremlin/server/handler/HttpGremlinEndpointHandler.java | 14 ++++---------- .../tinkerpop/gremlin/server/handler/HttpHandlerUtil.java | 7 ------- 2 files changed, 4 insertions(+), 17 deletions(-) diff --git a/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpGremlinEndpointHandler.java b/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpGremlinEndpointHandler.java index f0cb2b9ea2..7c474d6ba0 100644 --- a/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpGremlinEndpointHandler.java +++ b/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpGremlinEndpointHandler.java @@ -275,11 +275,7 @@ public class HttpGremlinEndpointHandler extends SimpleChannelInboundHandler<Requ // failures that follow this will show up in the response body instead. sendHttpResponse(ctx, OK, createResponseHeaders(ctx, serializer, requestCtx).toArray(CharSequence[]::new)); sendHttpContents(ctx, requestCtx); - // Skip if writeError() already terminated the response (e.g., serialization error in makeChunk). - // Sending a second LastHttpContent would corrupt the HTTP framing on keep-alive connections. - if (requestCtx.getRequestState() != RequestState.ERROR) { - sendLastHttpContent(ctx, HttpResponseStatus.OK, ""); - } + sendLastHttpContent(ctx, HttpResponseStatus.OK, ""); } catch (Throwable t) { writeError(requestCtx, formErrorResponseMessage(t, requestMessage), serializer.getValue1()); } finally { @@ -757,21 +753,19 @@ public class HttpGremlinEndpointHandler extends SimpleChannelInboundHandler<Requ ctx.setRequestState(STREAMING); return serializer.writeHeader(responseMessage, nettyContext.alloc()); } + ctx.setRequestState(FINISHED); - final ByteBuf fullResponse = serializer.serializeResponseAsBinary(ResponseMessage.build() + return serializer.serializeResponseAsBinary(ResponseMessage.build() .result(aggregate) .bulked(bulking) .code(HttpResponseStatus.OK) .create(), nettyContext.alloc()); - ctx.setRequestState(FINISHED); - return fullResponse; case STREAMING: return serializer.writeChunk(aggregate, nettyContext.alloc()); case FINISHING: - final ByteBuf footer = serializer.writeFooter(responseMessage, nettyContext.alloc()); ctx.setRequestState(FINISHED); - return footer; + return serializer.writeFooter(responseMessage, nettyContext.alloc()); } return serializer.serializeResponseAsBinary(responseMessage, nettyContext.alloc()); diff --git a/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpHandlerUtil.java b/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpHandlerUtil.java index 4fa5ba84ec..f0f6b652c0 100644 --- a/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpHandlerUtil.java +++ b/gremlin-server/src/main/java/org/apache/tinkerpop/gremlin/server/handler/HttpHandlerUtil.java @@ -97,13 +97,6 @@ public class HttpHandlerUtil { * @param serializer The serializer to use to serialize the error response. */ static void writeError(final Context context, final ResponseMessage responseMessage, final MessageSerializer<?> serializer) { - // Prevent writing after the response is already terminated. A second write would corrupt - // HTTP framing on keep-alive connections, poisoning them for subsequent requests. - if (context.getRequestState() == HttpGremlinEndpointHandler.RequestState.ERROR || - context.getRequestState() == HttpGremlinEndpointHandler.RequestState.FINISHED) { - return; - } - try { final ChannelHandlerContext ctx = context.getChannelHandlerContext(); final ByteBuf ByteBuf = context.getRequestState() == HttpGremlinEndpointHandler.RequestState.STREAMING
