1

I am implementing Single Sign-On functionality for automagically logging in to an affiliated https website using digest authentication. Currently my code is

URL url = new URL(protocol, ip, port, path);
URLConnection connection = url.openConnection(Proxy.NO_PROXY);
connection.connect();

if (connection != null && connection.getHeaderFields() != null) {
    if (connection.getHeaderFields().get(AUTHENTICATE_RESPONSE_HEADER) != null) {
        Map<String, String> authenticateParameters = identifyAuthentication(connection);

        String ha1 = calculateMD5(username + ":" + authenticateParameters.get("realm") + ":" + password);
        String ha2 = calculateMD5("GET" + ":" + path);
        String response = calculateMD5(ha1 + ":" + 
            authenticateParameters.get("nonce") + ":" +
            "00000001" + ":" +
            authenticateParameters.get("qop") + ":" +
            ha2);

            String authorizationRequest = authenticateParameters.get("challenge") + " " + 
                    "username=" + username + ", " +
                    "realm=" + authenticateParameters.get("realm") + ", " +
                    "nonce=" + authenticateParameters.get("nonce") + ", " +
                    "uri=" + path + ", " +
                    "qop=" + authenticateParameters.get("qop") + ", " +
                    "nc=" + "00000001" + ", " +
                    "response=" + response + ", " +
                    "opaque=" + authenticateParameters.get("opaque");

            connection.setAllowUserInteraction(true);
            connection.addRequestProperty(AUTHENTICATION_REQUEST_PROPERTY, authorizationRequest);
            connection.getHeaderFields();
    }
}

The problem is that I get

java.lang.IllegalStateException: Already connected
    at java.net.URLConnection.addRequestProperty(URLConnection.java:1061)
    at sun.net.www.protocol.http.HttpURLConnection.addRequestProperty(HttpURLConnection.java:2016)
    at com.ibm.net.ssl.www2.protocol.https.a.addRequestProperty(a.java:49)

which, I guess, makes sense but does not help me. How would I go about creating a request/response for logging in here (and eventually getting a sessionId)?

Thanks in advance.

2
  • Can we see the complete stacktrace? I'm unsure which line in your method is failing. Commented Nov 25, 2010 at 16:22
  • added - thanks for taking the time. Commented Nov 25, 2010 at 16:41

1 Answer 1

5

You cannot modify a connections request header when it has already been connected (you already sent a request header). You will have to make a new connection for the second request.

E.g.

connection = url.openConnection(Proxy.NO_PROXY);
connection.addRequestProperty(AUTHENTICATION_REQUEST_PROPERTY, authorizationRequest);
connection.getHeaderFields();

You can then get the sessionId or rather the cookie from the header.

It might be easier to use the apache HttpClient's Digest capability: http://hc.apache.org/httpclient-3.x/authentication.html

Sign up to request clarification or add additional context in comments.

4 Comments

making a new connection returns the same 401 reply as before.
But you do not get the original exception do you? Your authorizationRequest might not be correct. Whats the response header?
in the end I got this working using HttpClient. Much simpler and easier!
Great that this worked for you! Why dont you like to accept answers?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.