Secure your services with Active Directory user credentials

This post explains how you could secure your web srevices with Microsoft Active Directory[AD] user credentials.

In other words, your services could only be accessed by a set of users who belongs to a certain group in AD.

Let's start configuring AD first.

I have setup my AD on Windows 2003 Server [IP:192.168.1.3] and it looks like as shown in the image below.

In our case we'll be deploying our services with Axis2 running on Tomcat.

You can download Axis2 WAR distribution from here and deploy it on Tomcat.

In order to authenticate users against AD, Tomcat should have access to the AD user base.

Let's first create an AD user, which can be used by Tomcat to access AD.

This user can be of any name, we'll just say 'tomcat'.

Now we need to delegate the task, 'Read all user information' - to the user 'tomcat'.

[Users --> Right Click --> Delegate Control]

Done, with it. Lets create a new group called 'facilelogin' - where the members of this group will be given access to the secured web services.

Once created, add any user to that group - I'll add the 'administrator' - so, this user will be able to access secured services.

All set - we are done with the AD configurations - let's setup Tomcat.

Find the file [CATALINA_HOME]\conf\server.xml and edit to add the following.
<!-- You need to add new configurations inside this tag -->
<Engine name="Catalina" defaultHost="localhost">

<!-- Make sure you comment out this line from your current configuration -->
<!-- Realm className="org.apache.catalina.realm.UserDatabaseRealm" resourceName="UserDatabase"/ -->

<!-- Add following new configuration -->
<!-- Compare the values with the Active Directory image shown above -->  
<!-- I am running my AD on 192.168.1.3 -->    
<Realm className="org.apache.catalina.realm.JNDIRealm"
connectionName="cn=tomcat,cn=users,dc=home,dc=com"
connectionPassword="1qaz2wsx@"
connectionURL="ldap://192.168.1.3:389"
userRoleName="member"
userBase="cn=Users,dc=home,dc=com"
userPattern="cn={0},cn=Users,dc=home,dc=com"
roleBase="cn=Users,dc=home,dc=com"
roleName="cn"
roleSearch="(member={0})"
roleSubtress="false"
userSubtree="true"
/>

</Engine>
Once this is done - let's open the file [CATALINA_HOME]\webapps\axis2\WEB-INF\web.xml and edit to add the following.
<web-app> 

<security-constraint> 
<web-resource-collection>
<web-resource-name>secured services 
<url-pattern>/services/* 
</web-resource-collection>
<auth-constraint> 
<!-- This is mapped to the 'facilelogin' group in AD -->
<role-name>facilelogin 
</auth-constraint> 
</security-constraint> 

<login-config> 
<auth-method>BASIC 
<realm-name>facilelogin 
</login-config> 

</web-app>
All set - let's restart Tomcat.

Let's see how we could invoke the above secured service with a web service client.

Here, the only difference is you need to setup the HTTP header attributes appropriately.

Also, in this case user credentials are not carried by the SOAP header, but the transport header.
package org.apache.ws.axis2;

import java.util.Properties;

import org.apache.axiom.om.OMAbstractFactory;
import org.apache.axiom.om.OMElement;
import org.apache.axiom.om.OMFactory;
import org.apache.axiom.om.OMNamespace;
import org.apache.axis2.addressing.EndpointReference;
import org.apache.axis2.client.Options;
import org.apache.axis2.client.ServiceClient;
import org.apache.axis2.transport.http.HttpTransportProperties;

public class Client {

public static void main(String[] args) throws Exception {
ServiceClient client = null;
Options options = null;
OMElement response = null;
HttpTransportProperties.Authenticator authenticator = null;
Properties properties = null;

client = new ServiceClient();
options = new Options();
options.setAction("urn:getVersion");
options.setTo(new EndpointReference("http://localhost:8080/axis2/services/Version"));

authenticator = new HttpTransportProperties.Authenticator();
// Add user creadentials to the transport header
// This user belongs to the 'facilelogin' group in AD
authenticator.setUsername("administrator");
authenticator.setPassword("prabath");
authenticator.setRealm("facilelogin");

properties = new Properties();
properties.put(org.apache.axis2.transport.http.HTTPConstants.AUTHENTICATE, authenticator);

options.setProperties(properties); 
client.setOptions(options);

response = client.sendReceive(getPayload());

System.out.println(response);
}

private static OMElement getPayload() {
OMFactory factory = null;
OMNamespace ns = null;
OMElement elem = null;
factory = OMAbstractFactory.getOMFactory();
ns = factory.createOMNamespace("http://axisversion.sample", "ns1");
elem = factory.createOMElement("getVersion", ns); 
return elem;
}
}