Hi!
Since using OpenJDK 11 I noticed a behavioral change in the default retry
handling of HttpClient for https URLs caused by an implementation change in the
JDK.
AFAIK until including OpenJDK 10 Java was throwing SocketException directly for
both Socket and SSLSocket implementatons when they occurred.
With OpenJDK 11 now Java wraps those in SSLExceptions. Prior OpenJDK 11.0.3 the
subclass SSLProtocolException was (mistakenly) used, resulting in the following
bug report: https://bugs.openjdk.java.net/browse/JDK-8214339
After the fix with OpenJDK 11.0.3 / OpenJDK 12.0.1 it is still the base class
SSLException. Therefore the HttpClient's default retry implementation does no
longer retry Connection Resets happening while reading on an established
connection, because all SSLException are excluded from retries.
Here an example of interesting stackframes for OpenJDK 11.0.3:
javax.net.ssl.SSLException: Connection reset
at java.base/sun.security.ssl.Alert.createSSLException(Alert.java:127)
at
java.base/sun.security.ssl.TransportContext.fatal(TransportContext.java:321)
at
java.base/sun.security.ssl.TransportContext.fatal(TransportContext.java:264)
at
java.base/sun.security.ssl.TransportContext.fatal(TransportContext.java:259)
at
java.base/sun.security.ssl.SSLSocketImpl.handleException(SSLSocketImpl.java:1314)
at
java.base/sun.security.ssl.SSLSocketImpl$AppInputStream.read(SSLSocketImpl.java:839)
at
org.apache.http.impl.io.SessionInputBufferImpl.streamRead(SessionInputBufferImpl.java:139)
at
org.apache.http.impl.io.SessionInputBufferImpl.fillBuffer(SessionInputBufferImpl.java:155)
at
org.apache.http.impl.io.SessionInputBufferImpl.readLine(SessionInputBufferImpl.java:284)
at
org.apache.http.impl.conn.DefaultHttpResponseParser.parseHead(DefaultHttpResponseParser.java:140)
Thanks to the extensibility of HttpClient, it is quite easy to register an own
custom HttpRequestRetryHandler replacing the DefaultHttpRequestRetryHandler to
address the problem.
Now the question: What do others think - should the default implementation be
adjusted to also provide a behavior for OpenJDK >= 11 similar to those of
previous versions?
How could such a change look like? We now check the cause of SSLException.
Additionally I have another question in the context of retry handling. Wouldn't
it be more flexible, if the retry logging will be moved from
org.apache.http.impl.execchain.RetryExec#execute to the actual RetryHandler
implementation? The INFO logging in RetryExec is already too much for some
users (they will likely set the level of the logger to WARN) but containing too
less context information for others. If the logging would be in the
RetryHandler implementation itself, custom implementations/sub classes could
adjust it to the specific requirements. What do others say? Maybe I'm missing
something here.
Thanks,
Eric
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]