CAS-ify and Implement Single sign on in your application, Oh what a rellief…

 

Ah, there comes a time in a developers life when the application they develop requires to be actually used and in this particular case I am talking about multiple applications in the eco-system. Now this developer in discussion appears to be an enterprise scale geek. In order to use these applications, people need to be scrutinized by a central or single sign on like security entity. Here comes a Central Authentication Service to rescue your CASe.

 

I will take you through a set of steps here,

 

A. Configure CAS single sign on Server on a Tomcat with SSL configured.

Steps are detailed here.

B.. Create a service application to actually authenticate with this CAS server and service your request.

RESTful client for CAS secured services. A sample example is available here

 

C. Generate your SSL trusted certificates so that This CAS Server and your Service application can actually interact

Setup Certificates:   The SSL related certificates used for development are self-signed in nature and are restricted to IP on which server and services are running. The keytool command provisioned by the JDK is used for this purpose.

Self-Signed Certificate Setup steps for CAS:

  1. Configure: https://wiki.jasig.org/display/CASUM/RESTful+API
  2. Test : Using commons http client
  3.  Workflow,
  • - Get the TicketGrantingTicket from server = "https://localhost:8443/cas/v1/tickets";
  • - Get the ServiceTicket service = "https://localhost:8443/cas-sample/secure";
  • - Based on the service ticket GET access to the secured REST API service

D. Certification Path Exception for SSL handshake:
Reference: http://www.mkyong.com/webservices/jax-ws/suncertpathbuilderexception-unable-to-find-valid-certification-path-to-requested-target/
Source: https://github.com/vishwakarmarhl/javahelper/blob/master/InstallCert.java
Command: java InstallCert localhost:8443 // Also add trust for the service and cas_server IP

E. Use a Http Test client to authenticate and call the service.

 

Advertisements

Setup a CASified Secure Single sign on using the Central Authentication Service

The single sign on CAS server is a native java and spring based application and its best to build it yourself and deploy the WAR artifact to a SSL secured tomcat container.

A. Here are the pre-requisite for this setup:

  1. Java JDK 1.7
  2. Apache Tomcat 7
  3. Maven

B. Configure Tomcat 7 with the SSL configuration

  1. Configure the %TOMCAT_HOME%/conf/server.xml with the relevant path and password of the keystore as per the tag below. Here “${tomcat.base}/.keystore” is the path where the .keystore file needs to be saved. Comment out the AprLifecycleListener from the same configuration to avoid the “java.lang.Exception: Connector attribute SSLCertificateFile must be defined when using SSL with APR”
<Connector port="8443" protocol="HTTP/1.1" SSLEnabled="true" maxThreads="150" scheme="https" secure="true" clientAuth="false" sslProtocol="TLS"  keystoreFile="${tomcat.base}/.keystore" keystorePass="casmanion"/>

C. Generate the trust keystore

  • CD to the tomcat base folder ~/apache-tomcat-7.0.54/ and use the keytool to generate a .keystore file with the password configured in tomcat
  • keytool -genkeypair -dname "CN=127.0.0.1, OU=Vishwakarma, O=Rahul, L=Bangalore, ST=Karnataka, C=IN"  -alias rahul_casserver -keyalg RSA -ext san=ip:127.0.0.1 -keystore .keystore
  • Verify the store certificates by using, keytool -list -keystore .keystore
  • Start the tomcat server and see if it initializes properly after reading the SSL configuration

C. Create a Database and a user table to accomodate the user information in a MySQL server in root@localhost:3306

CREATE DATABASE IF NOT EXISTS `casdb` 
USE `casdb`;
DROP TABLE IF EXISTS `users`;
CREATE TABLE `users` (
 `user_id` int(11) NOT NULL AUTO_INCREMENT,
 `user_password` varchar(45) NOT NULL,
 `user_name` varchar(45) NOT NULL,
 `user_email` varchar(255) DEFAULT NULL,
 `user_creation_time` timestamp NULL DEFAULT CURRENT_TIMESTAMP,
 PRIMARY KEY (`user_id`),
 UNIQUE KEY `user_name_UNIQUE` (`user_name`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;'

INSERT INTO `casdb`.`users` (`user_id`, `user_password`, `user_name`, `user_email`) VALUES ('1', 'rahul', 'rahul', 'rahul_3766@yahoo.com');

D. Build and Deploy CAS with JDBC and restlets

  1. Obtain the latest release CAS Server from JASIG CAS download
  2. Rename the ~\CAS_Example\cas-server-4.0.0\modules\cas-server-webapp-4.0.0.war to cas.war
  3. Deploy this on tomcat webpps folder and start the server to test the bare deployment and then stop the server
  4. Add the JDBC and Restlet API authentication support. Copy cas-server-integration-restlet-4.0.0.jarcas-server-support-jdbc-4.0.0.jar to the ~/cas/WEB-INF/lib folder of the tomcat webapp deployment.
  5. Add the MySQL JDBC driver mysql-connector-java-5.1.6.jar and apache libraries org.apache.commons.dbcp.jar and org.apache.commons.pool.jar to ~/cas/WEB-INF/lib folder
  6. Time to configure the ~\apache-tomcat-7.0.54\webapps\cas\WEB-INF\deployerConfigContext.xml , Adding the JDBC authentication handler that will authenticate the entered credentials with the user & pass in the configured mysql datasource.
<!-- Adding the JDBC authentication related configuration --> 
<bean id="searchModeSearchDatabaseAuthenticationHandler" class="org.jasig.cas.adaptors.jdbc.SearchModeSearchDatabaseAuthenticationHandler" abstract="false" lazy-init="default" autowire="default" > 
   <property name="tableUsers"><value>users</value></property> 
   <property name="fieldUser"><value>user_name</value></property> 
   <property name="fieldPassword"><value>user_password</value></property> 
   <!--<property name="passwordEncoder" ref="defaultPasswordEncoder"/>--> 
   <property name="dataSource" ref="dataSource"/> 
</bean>
 <!-- Data source definition -->
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource">
<property name="driverClassName"> <value>com.mysql.jdbc.Driver</value> </property>
<property name="url">
<value>jdbc:mysql://localhost:3306/casdb</value>
</property>
<property name="username"><value>root</value></property>
<property name="password"><value></value></property>
</bean>
<bean id="defaultPasswordEncoder" class="org.jasig.cas.authentication.handler.DefaultPasswordEncoder">
<constructor-arg value="SHA-256" />
</bean>
Also, We need to Add the reference to this bean in the authenticationManager beans constructor-arg map entry as follows:

<entry key-ref="searchModeSearchDatabaseAuthenticationHandler" value-ref="primaryPrincipalResolver" />

E. Test your standalone CAS Server for authentication

  1. Start your tomcat and make sure there is no error on the startup and all the dependencies are resolved
  2. Test the login using https://127.0.0.1:8443/cas/login and user/pass as rahul/rahul
  3. Test the logout using https://127.0.0.1:8443/cas/logout
  4. Here is a curl test that needs to be verified. curl -X POST –data “username=rahul&password=rahul” https://127.0.0.1:8443/cas/v1/tickets –cacert “C:\Dev\CAS_Example\apache-tomcat-7.0.54\.keystore”

F. The deployed artifact “cas” can be found as a zip at GITHUB: https://github.com/vishwakarmarhl/CASifiedExamples.git