Search code examples
javahttpconnection

NPE in sun.net.www.protocol.http.HttpURLConnection.plainConnect()


I'm working on an application that runs in a JBoss 7 environment and thus is bound to use Java 7 at max (AFAIK JBoss 7 doesn't run on Java 8+ because they did some dirty tricks or used something that changed from Java 7 to 8 (source).

The problem I'm facing is this: I do a request to some remote https url which only supports TLSv1.2 and the first request is successful.

Any further request fails though with the following exception:

Caused by: java.lang.NullPointerException
    at sun.net.www.protocol.http.HttpURLConnection.plainConnect(HttpURLConnection.java:986)
    at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.connect(AbstractDelegateHttpsURLConnection.java:177)
    at sun.net.www.protocol.http.HttpURLConnection.getOutputStream(HttpURLConnection.java:1092)
    at sun.net.www.protocol.https.HttpsURLConnectionImpl.getOutputStream(HttpsURLConnectionImpl.java:250)
    at <our code>

<our code> looks like this:

URL url = new URL( "https://..." );    
URLConnection urlConnection = url.openConnection(); 
urlConnection.setUseCaches( false );
urlConnection.setRequestProperty( "User-Agent", "java.net.URLConnection/" );

//Here's where we finally get the exception
OuputStream out = urlConnection.getOutputStream(); 

Normally an NPE isn't that big a problem, just a little debugging helps spot the error. However, since it happens in proprietary classes (sun.net. ....) I can't get the sources for those, at least not in a version which seems correct (one version looks like this at like 986: connected = true; - hardly a source for an NPE).

This happens in both Oracle JDK 1.7.0u80 and OpenJDK 7u75.

Any ideas?


Solution

  • Finally found the error, thanks to some help by @yole.

    The sources are not exact so I can't be 100% sure about the actual cause but in our case there was a custom ProxySelector registered and the exception seems to have been thrown when calling this code which is part of plainConnect() and somewhere around line 986:

      ProxySelector sel =
        java.security.AccessController.doPrivileged(
          new java.security.PrivilegedAction<ProxySelector>() {
            public ProxySelector run() {
              return ProxySelector.getDefault();
            }
          });
    

    As I said the sources were off because I couldn't find the exact version but looking for custom ProxySelector related code helped at lot (and as in 99.9% of the cases it was our code that caused the problem somehow).

    That still doesn't explain the NPE because all versions I could find were either setting some boolen flag, comments or handling an IOException (either the catch-clause or a plain rethrow) but since removing the custom selector solved the problem I'm happy.

    I hope if anyone else stumbles over a similar problem this will help save them some headaches.