Monday, March 03, 2014

Handle NTLM authentication with HttpClient v4.0.1 (Websphere application server v8.5)

I tried to use Apache HttpClient v4.3.3 in one of my jax-rs service implementation, which is deployed to websphere applciation v8.5.
However, the code always reported the issue that the INSTANCE field is not present in BasicLineFormatter class. It turned out that in one of the plugin jar file of WAS (com.ibm.ws.prereq.jaxrs.jar), the old version of HttpClient is included. According to the version properties file, the version is 4.0.1.
The problem came because HttpClient v4.0.1 doesn't support NTLM authentication, which is required for my service. I had to find a way to change the order of class loading of the web application. I tried a few options such as making the class loading using "parent last", adding the library to JRE path, and so on. None of them worked out.
Eventually I had to go with the v4.0.1 version which is shipped with WAS v8.5. Information provided on http://hc.apache.org/httpcomponents-client-4.3.x/ntlm.html is mostly correct, except that it applies with v4.3.3. Here's the instruction for using SAMBA JCIFS with v4.0.1:
1. Create NTLMEngine with the instructions on http://hc.apache.org/httpcomponents-client-4.3.x/ntlm.html .
2. Implement AuthSchemeFactory instead of AuthSchemeProvider for v4.3.3.
public class JCIFSNTLMSchemeFactory implements AuthSchemeFactory {@Override
public AuthScheme newInstance(HttpParams arg0) {
return new NTLMScheme(new JCIFSEngine());
}
}
3. Use the following code as an example to register the AuthSchemeFactory and create NTLM credential :
DefaultHttpClient httpclient = new DefaultHttpClient();
httpclient.getAuthSchemes().register("ntlm",new JCIFSNTLMSchemeFactory());
CredentialsProvider credsProvider = new BasicCredentialsProvider();
NTCredentials ntcred = new NTCredentials(username, password,
InetAddress.getLocalHost().getHostName(), domain);
credsProvider.setCredentials(new AuthScope(hostname, port,
AuthScope.ANY_REALM, "NTLM"), ntcred);
httpclient.setCredentialsProvider(credsProvider);
In this way, the NTLM support is done on WAS v8.5.
Normally sharepoint site use SSL for communication. The client certificate needs to be imported into the truststore of WAS. Otherwise, "SSL HANDSHAKE FAILURE" will be reported.

No comments: