-
Notifications
You must be signed in to change notification settings - Fork 2.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix retrying requests with body contents by resetting the reader index of ByteBuf #1281
Conversation
@@ -178,6 +178,13 @@ public Iterable<HttpContent> getBodyContents() { | |||
return Collections.unmodifiableList(bodyChunks); | |||
} | |||
|
|||
@Override | |||
public void resetBodyReader() { | |||
for (final HttpContent chunk : bodyChunks) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is it worth only resetting this when we know we have a body, i.e. effectively setBody
has been called?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looking at the soft contract we don't set the hasBody
boolean in the setBody
method. So going to not check that here as the hasBody doesn't determine any logic within the message impl currently.
LGTM! This is a huge improvement over the hack we put in back in 2018. |
@@ -896,6 +846,10 @@ protected void handleOriginNonSuccessResponse(final HttpResponse originResponse, | |||
startedSendingResponseToClient, zuulRequest.hasCompleteBody(), zuulRequest.getMethod()); | |||
//detach from current origin. | |||
unlinkFromOrigin(); | |||
|
|||
// ensure body reader indexes are reset so retry is able to access the body buffer |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Worth clarifying in this comment that we want Netty to have access to that ByteBuf, rather than Zuul itself.
For TLS handled connections, once the request body has been written to the channel, the ByteBuf.readerIndex is mutated to point to the end of the buffer. This means when retrying requests, subsequent fetches of that buffer return no bytes (as they use the readerIndex). This only affects TLS connections as the SSL handler in netty mutates those indexes (doesn't appear to be the case with plaintext).
Original issue raised with netty from 2018 (netty/netty#7753) eluded to this fact before the changes to pre-buffer bodies was put into zuul (i.e. pre-buffering on 503s that was introduced hid this actual issue of the indexes needing to be reset).
This change resets the readerIndex before retrying a request, and removes the buffering of bodies in retry scenarios.