Use standard HTTP mechanism to surface truncated query responses #13492
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Description
As of now, executing a query can sometimes give truncated results. This can happen when the server starts streaming the response to the client but fails before the whole response has been streamed back. The most common situation here is query timeout. If all the results are not streamed back in the
timeout
period, then the response gets cut. The client sees a 200 OK response and tries to parse the JSON.We have built some solutions for this. There is no generic solution but implemented depending on the result format (CSV, Array, Object, etc.) and query protocol (SQL/JSON). We add some newline characters and if the client doesn't see those newline characters at the end, it considers the response truncated. This, however, doesn't work with clients that speak standard HTTP language such as curl.
There is a provision in the chunked encoding mechanism to signal truncated responses. The server sends a final terminating chunk and the client uses that terminating chunk to confirm that response is complete. Jetty is supposed to do the same but for some reason, it sends a terminating chunk even if the response is incomplete. I verified this by running Wireshark locally and inspecting the frames
For a truncated response
For a complete response
But then, I also found this commit that clearly has a fix and even a test case to verify the behavior we want.
After doing a bit more fiddling, I realized that we are closing the
ResultWriter
inSqlResource
try-block and that, in turn, closes the response output stream. That effectively signals the end of the response and the timeout exception in the query is thrown afterward. At this point, throwing an exception would likely have no effect on the response bits being sent by Jetty.To fix this, I have disabled the auto-closing of the target output stream in all of the writers used in SqlResource. I have modified the docs of
ResultWriter#close
to call out explicitly that they must not close the output stream.Here is what I get using a
curl
command to issue a queryBefore the fix
After the fix
Release note
Key changes
This PR has: