Sunday, February 13, 2011

Spring Security 3 - OpenID with Javascript OpenID Selector

Introduction

In previous tutorials we've discussed how to add OpenID support to an existing Spring Security 3 application using various OpenID providers. We added each provider manually, including the images and specialized URLs. However that solution has introduced a couple of issues:

Problems

1. We're forced to manually add all OpenID providers in the JSP page. Developer A might implement it differently versus Developer B. This means users do not get a unified user experience.

2. Users are still required to know their full OpenID login. For example, to login using Blogspot, the user will type http://krams915.blogspot.com. Ideally the user should only type his username, i.e. krams915. Typing the full URL is error-prone, especially for non-technical users.

3. We could implement our own Javascript library that will parse and concatenate the default OpenID URLs. But that introduces extra work, and again, multiple developers may implement it differently. Also, are you expert enough to start your own Javascript framework?

Solution

Luckily for us there is a solution: the Javascript OpenID Selector

What is Javascript OpenID Selector?
This is a simple Javascript OpenID selector. It has been designed so that users do not even need to know what OpenID is to use it, they simply select their account by a recognisable logo.

Source: http://code.google.com/p/openid-selector/

You can find a live demo of this project at http://openid-selector.googlecode.com/svn/trunk/demo.html

Development

In this tutorial we'll add OpenID login support to an existing Spring Security 3 application. That means we'll be reusing existing configuration.

To fully appreciate this tutorial, it's required you know how to setup a simple Spring Security application using a simple user-service. If you need a review, please read my other guide Spring MVC 3 - Security - Using Simple User-Service.

You are also advised to read my other OpenID tutorials to understand the problem that we're trying to solve. You can check the following Spring Security 3 - OpenID Login with Google Provider and Spring Security 3 - OpenID Login with myOpenID Provider

We will based our application from the one we developed for Spring MVC 3 - Security - Using Simple User-Service tutorial. This is because the changes we need to implement are just a matter of configuration and placing Javascript snippets.

Preview

Before we add the Javascript OpenID Selector, our login page looks like the following:


After adding the Javascript OpenID Selector, our new login page should look like below:


Do you see the big improvement? We've just added multiple OpenID providers by just editing a JSP file which we'll show later.

Adding Javascript OpenID Selector

Since this is a third-party project, we must download it first and place the necessary files to the current Spring project. Here are the steps:

1. Visit the project's site at http://code.google.com/p/openid-selector/

2. Go to the Downloads section. Find the latest open-selector project:

3. Download and save the file.

4. Extract and open the extracted folder:


You should see a list of folders and files. We're only interested with the following:
js/jquery-1.2.6.min.js
js/openid-jquery.js
js/openid-en.js
images folder
css folder

5. Copy these files to the resources folder of the Spring project:

I suggest you create the following folders to logically contain these files.
css
images
js

Our next step is to edit the application's JSP login page to display the Javascript OpenID Selector.

6. Go back to the folder where you extracted the open-selector project.

7. Open the demo.html to see the following:


Right-click on this html file and view its source:

demo.html
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
 <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
 <title>JQuery Simple OpenID Selector Demo</title>
 <!-- Simple OpenID Selector -->
 <link type="text/css" rel="stylesheet" href="css/openid.css" />
 <script type="text/javascript" src="js/jquery-1.2.6.min.js"></script>
 <script type="text/javascript" src="js/openid-jquery.js"></script>
 <script type="text/javascript" src="js/openid-en.js"></script>
 <script type="text/javascript">
  $(document).ready(function() {
   openid.init('openid_identifier');
   openid.setDemoMode(true); //Stops form submission for client javascript-only test purposes
  });
 </script>
 <!-- /Simple OpenID Selector -->
 <style type="text/css">
  /* Basic page formatting */
  body {
   font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
  }
 </style>
</head>

<body>
 <h2>JQuery Simple OpenID Selector Demo</h2>
 <p>This is a simple example to show how you can include the Javascript into your page.</p>
 <br/>
 <!-- Simple OpenID Selector -->
 <form action="examples/consumer/try_auth.php" method="get" id="openid_form">
  <input type="hidden" name="action" value="verify" />
  <fieldset>
   <legend>Sign-in or Create New Account</legend>
   <div id="openid_choice">
    <p>Please click your account provider:</p>
    <div id="openid_btns"></div>
   </div>
   <div id="openid_input_area">
    <input id="openid_identifier" name="openid_identifier" type="text" value="http://" />
    <input id="openid_submit" type="submit" value="Sign-In"/>
   </div>
   <noscript>
    <p>OpenID is service that allows you to log-on to many different websites using a single indentity.
    Find out <a href="http://openid.net/what/">more about OpenID</a> and <a href="http://openid.net/get/">how to get an OpenID enabled account</a>.</p>
   </noscript>
  </fieldset>
 </form>
 <!-- /Simple OpenID Selector -->
</body>
</html>

8. Copy the code inside head and body section. Paste the code in the corresponding sections of the JSP login page. Here's the final JSP page:

loginpage.jsp
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib uri="http://www.springframework.org/tags/form" prefix="form" %>
<%@ taglib uri="http://www.springframework.org/tags" prefix="spring" %>

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
 
 <c:url var="rootUrl" value="/resources/" />
 
 <title>JQuery Simple OpenID Selector Demo</title>
 <!-- Simple OpenID Selector -->
 <link type="text/css" rel="stylesheet" href="${rootUrl}css/openid.css" />
 <script type="text/javascript" src="${rootUrl}js/jquery-1.2.6.min.js"></script>
 <script type="text/javascript" src="${rootUrl}js/openid-jquery.js"></script>
 <script type="text/javascript" src="${rootUrl}js/openid-en.js"></script>
 <script type="text/javascript">
  $(document).ready(function() {
   openid.init('openid_identifier');
   //openid.setDemoMode(true); //Stops form submission for client javascript-only test purposes
   });
 </script>
 <!-- /Simple OpenID Selector -->
 <style type="text/css">
 /* Basic page formatting */
 body {
  font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
 }
 </style>
</head>
<body>

<h1>Spring Security 3</h1>
<div id="login-error">${error}</div>

<c:url var="openIDLoginUrl" value="/j_spring_openid_security_check" />
<h2>JQuery Simple OpenID Selector Demo</h2> 
 <p>This is a simple example to show how you can include the Javascript into your page.</p> 
 <br/> 
 <!-- Simple OpenID Selector --> 
 <form action="${openIDLoginUrl}" method="post" id="openid_form"> 
  <input type="hidden" name="action" value="verify" /> 
  <fieldset> 
   <legend>Sign-in or Create New Account</legend> 
   <div id="openid_choice"> 
    <p>Please click your account provider:</p> 
    <div id="openid_btns"></div> 
   </div> 
   <div id="openid_input_area"> 
    <input id="openid_identifier" name="openid_identifier" type="text" value="http://" /> 
    <input id="openid_submit" type="submit" value="Sign-In"/> 
   </div> 
   <noscript> 
    <p>OpenID is service that allows you to log-on to many different websites using a single indentity.
    Find out <a href="http://openid.net/what/">more about OpenID</a> and <a href="http://openid.net/get/">how to get an OpenID enabled account</a>.</p>
   </noscript> 
  </fieldset> 
 </form> 
 <!-- /Simple OpenID Selector --> 

</body>
</html>

To make this code work, we have to correctly set the root URL by using a JSTL tag library:
<c:url var="rootUrl" value="/resources/" />
We've also commented out the following line which is responsible for activating the demo function:
//openid.setDemoMode(true); //Stops form submission for client 

Try running the application. You'll notice the images are missing. That's because we need to set the correct image path property inside the openid-jquery.js.

9. Go to the resources folder. Open the openid-jquery.js file.

10. Find the img_path property. Set the value as follows:
img_path : '../../resources/images/',

Run the Application

To run the application, use the following URL to display the login page:
http://localhost:8080/spring-security-openid-selector/krams/auth/login

Here's the final screenshot:

Try playing with all the various OpenID providers. Notice how user-friendly the interface is.

Reminder

Notice regardless whether you've entered the correct credentials the Spring application still throws out an error that the username or password is incorrect. That's because you need to add the correct OpenID identifier under the user-service tag. See the spring-security.xml

<security:user-service id="userDetailsService">
   <!-- user name is based on the returned open id identifier -->
   <!-- YOU MUST MANUALLY ADD THE RETURNED OPENID IDENTIFIER HERE -->
     <security:user name="http://krams915.blogspot.com/" password="" authorities="ROLE_USER, ROLE_ADMIN" />
  </security:user-service>

Conclusion

That's it. We've managed to add the Javascript OpenID Selector. Of course to make the whole project work, you need to add the corresponding returned OpenID identifiers in the Spring Security's in-memory user-service. If you're going to test these with Google, Yahoo, or any of your favorite providers, please log out first so that you can test the login functionality!

The best way to learn further is to try the actual application.

Download the project
You can access the project site at Google's Project Hosting at http://code.google.com/p/spring-security-openid/

You can download the project as a Maven build. Look for the spring-security-openid-selector.zip in the Download sections.

You can run the project directly using an embedded server via Maven.
For Tomcat: mvn tomcat:run
For Jetty: mvn jetty:run

If you want to learn more about Spring MVC and integration with other technologies, feel free to read my other tutorials in the Tutorials section.
StumpleUpon DiggIt! Del.icio.us Blinklist Yahoo Furl Technorati Simpy Spurl Reddit Google I'm reading: Spring Security 3 - OpenID with Javascript OpenID Selector ~ Twitter FaceBook

Subscribe by reader Subscribe by email Share

Spring Security 3 - OpenID Login with Google Provider

In this tutorial we'll add OpenID support for authenticating users in our existing Spring Security 3 application. It's required you understand how to setup a simple Spring Security application using a simple user-service. If you need a review, please read my other guide Spring MVC 3 - Security - Using Simple User-Service for an in-depth tutorial. We will use Google as our OpenID provider. You are therefore required to setup an account with Google.

We will based our application from the one we developed for Spring MVC 3 - Security - Using Simple User-Service tutorial. This is because everything is exactly the same. It's just a matter of configuration to enable OpenID support.

What is OpenID?
OpenID allows you to use an existing account to sign in to multiple websites, without needing to create new passwords.

You may choose to associate information with your OpenID that can be shared with the websites you visit, such as a name or email address. With OpenID, you control how much of that information is shared with the websites you visit.

With OpenID, your password is only given to your identity provider, and that provider then confirms your identity to the websites you visit. Other than your provider, no website ever sees your password, so you don’t need to worry about an unscrupulous or insecure website compromising your identity.

Source: http://openid.net/get-an-openid/what-is-openid/

Screenshot

Here's a screenshot of the application's OpenID login page:


Review

Enabling OpenID authentication is actually simple. Remember our application is based on the Spring MVC 3 - Security - Using Simple User-Service. Because of that all we need to do is modify the existing spring-security.xml config.

The Old Config

Here's our existing config file (for a thorough explanation please read the aforementioned guide):

spring-security.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:security="http://www.springframework.org/schema/security"
 xsi:schemaLocation="http://www.springframework.org/schema/beans 
      http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
   http://www.springframework.org/schema/security 
   http://www.springframework.org/schema/security/spring-security-3.0.xsd">
 
 <!-- This is where we configure Spring-Security  -->
 <security:http auto-config="true" use-expressions="true" access-denied-page="/krams/auth/denied" >
 
  <security:intercept-url pattern="/krams/auth/login" access="permitAll"/>
  <security:intercept-url pattern="/krams/main/admin" access="hasRole('ROLE_ADMIN')"/>
  <security:intercept-url pattern="/krams/main/common" access="hasRole('ROLE_USER')"/>
  
  <security:form-login
    login-page="/krams/auth/login" 
    authentication-failure-url="/krams/auth/login?error=true" 
    default-target-url="/krams/main/common"/>
   
  <security:logout 
    invalidate-session="true" 
    logout-success-url="/krams/auth/login" 
    logout-url="/krams/auth/logout"/>
 
 </security:http>
 
 <!-- Declare an authentication-manager to use a custom userDetailsService -->
 <security:authentication-manager>
         <security:authentication-provider user-service-ref="userDetailsService">
           <security:password-encoder ref="passwordEncoder"/>
         </security:authentication-provider>
 </security:authentication-manager>
 
 <!-- Use a Md5 encoder since the user's passwords are stored as Md5 in the database -->
 <bean class="org.springframework.security.authentication.encoding.Md5PasswordEncoder" id="passwordEncoder"/>

  <!-- An in-memory list of users. No need to access an external database layer.
      See Spring Security 3.1 Reference 5.2.1 In-Memory Authentication -->
  <!-- john's password is admin, while jane;s password is user  -->
  <security:user-service id="userDetailsService">
     <security:user name="john" password="21232f297a57a5a743894a0e4a801fc3" authorities="ROLE_USER, ROLE_ADMIN" />
     <security:user name="jane" password="ee11cbb19052e40b07aac0ca060c23ee" authorities="ROLE_USER" />
   </security:user-service>
 
</beans>
This configuration uses Spring Security's form-based login where you enter a username and password. At the end of the file, we have declared a list of users with corresponding credentials.

To authenticate a user, he must first provide a username and password which the application will compare in the in-memory list as declared in the user-service tag. If a match is found, the user is authenticated and authorized.

The New Config

Here's our new config file which enables OpenID support. Notice almost everything is still exactly the same!

spring-security.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:security="http://www.springframework.org/schema/security"
 xsi:schemaLocation="http://www.springframework.org/schema/beans 
      http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
   http://www.springframework.org/schema/security 
   http://www.springframework.org/schema/security/spring-security-3.0.xsd">
 
 <!-- This is where we configure Spring-Security  -->
 <security:http auto-config="true" use-expressions="true" access-denied-page="/krams/auth/denied" >
 
  <security:intercept-url pattern="/krams/auth/login" access="permitAll"/>
  <security:intercept-url pattern="/krams/main/admin" access="hasRole('ROLE_ADMIN')"/>
  <security:intercept-url pattern="/krams/main/common" access="hasRole('ROLE_USER')"/>
  
  <!-- Adding the openid-login tag activates Spring Security's support for OpenID  -->
  <security:openid-login
    login-page="/krams/auth/login" 
    authentication-failure-url="/krams/auth/login?error=true" 
    default-target-url="/krams/main/common"/>
   
  <security:logout 
    invalidate-session="true" 
    logout-success-url="/krams/auth/login" 
    logout-url="/krams/auth/logout"/>
 
 </security:http>
 
 <!-- Declare an authentication-manager to use a custom userDetailsService -->
 <security:authentication-manager>
         <security:authentication-provider user-service-ref="userDetailsService">
           <security:password-encoder ref="passwordEncoder"/>
         </security:authentication-provider>
 </security:authentication-manager>
 
 <!-- Use a Md5 encoder since the user's passwords are stored as Md5 in the database -->
 <bean class="org.springframework.security.authentication.encoding.Md5PasswordEncoder" id="passwordEncoder"/>

  <!-- An in-memory list of users. No need to access an external database layer.
      See Spring Security 3.1 Reference 5.2.1 In-Memory Authentication -->
  <security:user-service id="userDetailsService">
   <!-- user name is based on the returned OpenID identifier from Google -->
     <security:user name="https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E" 
          password="" authorities="ROLE_USER, ROLE_ADMIN" />
  </security:user-service>
 
</beans>

Google: Enabling OpenID

With OpenID the same principle applies. To authenticate a user via Google's OpenID support, he must perform the following steps:

1. Click the Sign with Google button.


2. Login with the OpenID provider.


After a successful authentication, the provider will ask the user to continue and return back to the original application

4. Spring Security will then perform two additional steps:
- Check if the returned OpenID identifier is registered in the application's database.
- Check if the returned OpenID identifier has authorities assigned in the application's database.

Notice these are the same steps used in a form-based login. This is the reason why it's beneficial that you understand how to setup a simple Spring Security 3 application using a simple user-details service first.

Authorities/Roles

Take note the job of the OpenID provider is to authenticate the user and returned back a valid OpenID identifier. The appropriate authorities or roles is the responsibility of the application. We must assign the roles in other words!
<security:user-service id="userDetailsService">
   <!-- user name is based on the returned open id identifier -->
     <security:user name="https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E" 
          password="" authorities="ROLE_USER, ROLE_ADMIN" />
  </security:user-service>
Notice for this username we assigned a ROLE_USER and ROLE_ADMIN.

Development

Let's enable OpenID authentication by modifying the config file. We just need to perform two steps:

1. Replace the form-login tag with openid-login tag
old config
<security:http auto-config="true" >
    <security:form-login >
    ...omitted declarations
</security:http>

new config
<security:http auto-config="true" >
    <security:openid-login >
    ...omitted declarations
</security:http>

2. Add a new user name inside the user-service tag
<security:user-service id="userDetailsService">
     <security:user name="https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E" 
          password="" authorities="ROLE_USER, ROLE_ADMIN" />
  </security:user-service>
Notice the password attribute is empty. That's because the actual authentication is performed by the OpenID provider. The user name is based on the OpenID identifier returned by the provider. By default the OpenID login format is:
http://USERNAME.myopenid.com/
where USERNAME is a placeholder for the user's chosen username during registration at myOpenID website.

However Google doesn't follow this convention. Instead the returned OpenID identifier has the following format:
https://www.google.com/accounts/o8/id?id=XXXXXXXXXXXXXXXXXXXXX
For example:
https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E

The JSP Login Page

Since we'll be using OpenID, we need to modify our JSP login page to use the OpenID form identifiers.

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib uri="http://www.springframework.org/tags/form" prefix="form" %>
<%@ taglib uri="http://www.springframework.org/tags" prefix="spring" %>

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>

<h1>Login</h1>
<div id="login-error">${error}</div>

<c:url var="logoUrl" value="/resources/openidlogosmall.png" />
<p><img src="${logoUrl}"></img>Login with OpenID:</p>
<c:url var="openIDLoginUrl" value="/j_spring_openid_security_check" />
<form action="${openIDLoginUrl}" method="post" >
 <label for="openid_identifier">OpenID Login</label>:
 <input id="openid_identifier" name="openid_identifier" type="text"/>
 <input  type="submit" value="Login"/>        
</form>

<hr/>

<c:url var="googleLogoUrl" value="/resources/google-logo.png" />
<img src="${googleLogoUrl}"></img>
<form action="${openIDLoginUrl}" method="post">
    For Google users:
   <input name="openid_identifier" type="hidden" value="https://www.google.com/accounts/o8/id"/>
   <input type="submit" value="Sign with Google"/>
</form>

</body>
</html>
Notice we have two form tags.

The first form tag is for OpenID providers that support direct id entry. For example, http://krams915.myopenid.com or http://krams915.blogspot.com. For a description of this form tag, see the tutorial Spring Security 3 - OpenID Login with myOpenID Provider

Google doesn't support direct id entry. Instead you need to use the following URL as the entry id:
https://www.google.com/accounts/o8/id
This works. However, the user must remember this exact URL which is bad because the majority of users will not remember that URL ever! Talk about bad user experience.

To resolve this issue, we added a second form tag that only works for Google. What we did here is hide the input text field and embed Google's default entry id (https://www.google.com/accounts/o8/id) so that when the user clicks the Sign with Google button, he doesn't need to type that unfriendly URL.

Determine the OpenID Identifier

The best way to determine the OpenID identifier is to set the application's logger to DEBUG level. Then run the application and check the logs. Of course, you need to have a working internet connection to be able to login with the provider. Our application uses log4j for logging.

Here's the log4j properties file:

log4j.properties
log4j.rootLogger=DEBUG,console

#Console Appender 
log4j.appender.console=org.apache.log4j.ConsoleAppender
log4j.appender.console.layout=org.apache.log4j.PatternLayout
log4j.appender.console.layout.ConversionPattern=[%5p] [%t %d{hh:mm:ss}] (%F:%M:%L) %m%n

#Custom assignments
log4j.logger.controller=DEBUG,console
log4j.logger.service=DEBUG,console

#Disable additivity
log4j.additivity.controller=false
log4j.additivity.service=false

Run the application and login with OpenID. After a successful authentication, check the logs. Here's a sample output:

log output
[DEBUG] [http-8080-Processor23 02:33:21] (Association.java:sign:261) Computing signature for input data:
op_endpoint:https://www.google.com/accounts/o8/ud
claimed_id:https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E
identity:https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E
return_to:http://localhost:8080/spring-security-openid-google/j_spring_openid_security_check
response_nonce:2011-02-12T15:48:26Zdji30Q3btZj2Cw
assoc_handle:AOQobUebACOhT-Hh3ckKxe8Bxc_drPGqIIfzMcYDBfU0167YQZw6J4F6uvH18g2UlNRDPC7B

[DEBUG] [http-8080-Processor24 11:48:27] (Association.java:sign:267) Calculated signature: Mq8Iu1XQ87rKQePQxEnIcU7GttlT6E1usz3E+BgGvx4=
[DEBUG] [http-8080-Processor24 11:48:27] (ConsumerManager.java:verifySignature:1790) Local signature verification succeeded.
[ INFO] [http-8080-Processor24 11:48:27] (ConsumerManager.java:verifySignature:1850) Verification succeeded for: https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E
[DEBUG] [http-8080-Processor24 11:48:27] (ProviderManager.java:doAuthentication:127) Authentication attempt using org.springframework.security.openid.OpenIDAuthenticationProvider
Pay attention to these values:
claimed_id:https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E
identity:https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E
The claimed_id is what you need to add in the application's user-details table. In our case, it's an in-memory list.

If you really want to ensure that you're using the correct id, check the next line in the log file:
[ INFO] [http-8080-Processor24 11:48:27] (ConsumerManager.java:verifySignature:1850) Verification succeeded for: https://www.google.com/accounts/o8/id?id=AItxxioJSDLFJLjxcksdfjOpAASDFosSSoJ0E
The value you see here is the id that must be placed in the user-details table. I'm adding emphasis here because if you're using other OpenID providers, you might get confused which id to used. This one is always correct.

Other OpenID Providers

Below is a sample table that shows the different identifiers returned by various OpenID providers (We'll try to expand this list as we explore OpenID further in future tutorials):

MyOpenID http://krams915.myopenid.com/
Yahoo https://me.yahoo.com/a/ooXDFSsdfsqDbYAGuDSFSIK.PIuBsfdKA--#ade71
Google https://www.google.com/accounts/o8/id?id=BVlajJOIDjsldfjszSfjsM5sdfs0E
Blogspot http://krams915.blogspot.com/

Notice some OpenID providers adhere to the standard format, but others do not. To see other availabe OpenID providers, please visit http://openid.net/get-an-openid/

Run the Application

To run the application, use the following URL:
http://localhost:8080/spring-security-openid-myopenid/krams/auth/login
Of course, you will need to modify the username in the user-details service to match your provider's returned OpenID identifier. You will need to run the application first, authenticate, after a failed authentication, you should be able to see the claimed_id in the logs.

Conclusion

That's it. We've managed to enable OpenID support on our existing Spring Security 3 application by just modifying two simple configurations and a single JSP file. We've also discussed how to retrieve the OpenID identifier and how Spring Security evaluates this property.

The best way to learn further is to try the actual application.

Download the project
You can access the project site at Google's Project Hosting at http://code.google.com/p/spring-security-openid/

You can download the project as a Maven build. Look for the spring-security-openid-google.zip in the Download sections.

You can run the project directly using an embedded server via Maven.
For Tomcat: mvn tomcat:run
For Jetty: mvn jetty:run

If you want to learn more about Spring MVC and integration with other technologies, feel free to read my other tutorials in the Tutorials section.
StumpleUpon DiggIt! Del.icio.us Blinklist Yahoo Furl Technorati Simpy Spurl Reddit Google I'm reading: Spring Security 3 - OpenID Login with Google Provider ~ Twitter FaceBook

Subscribe by reader Subscribe by email Share