Plugin Tutorial : Creating a HttpAutoLoginPlugin for Enonic CMS 4.4
A common scenario for many larger-scale companies is to implement some sort of identity management system. The rationale for implementing such a system is to ensure a unified policy for authentication and authorization across all corporate intranets and extranets, often with a complex infrastructure.
So where does Enonic CMS fit in, in this scenario?
When implementing a security framework you leave all your authentication and authorization concerns to the service. So when the http-request hits Enonic CMS, the user and request has already passed clearance. That means that Enonic CMS doesn’t have to do it.
So your first step would be to get rid of the existing Enonic CMS login and then implement a HttpAutoLoginPlugin. The plugin then automatically logs in the user into Enonic CMS when certain rules are met. In this tutorial this is the presence of a valid http request header.
In our example we’ll assume that we are using IBM Tivoli Access Manager/WebSeal, so the header we are looking for is named “iv-user”.
But first, a brief description of how WebSeal works:
WebSEAL normally acts as a reverse Web proxy by receiving HTTP/HTTPS requests from a Web browser and delivering content from its own Web server or from junctioned back-end Web application servers. Requests passing through WebSEAL are evaluated by the Tivoli Access Manager authorization service to determine whether the user is authorized to access the requested resource
Source:
IBM Tivoli Access Manager & WebSEAL
With HttpAutoLoginPlugin, you are required to implement the getAuthenticatedUser() and validateCurrentUser() methods.
The HttpAutoLoginPlugin is only called if the user do not have a valid logged-in session. If the session is in “logged in” state, the getAuthenticatedUser will not be evaluated. However, the validateCurrentUser will always be evaluated. This makes is possible to check if the header is still present, or perform other checks to ensure that the user still has a valid login from the 3rd party system.
Problem description:
When authenticating through security service layer independent, Enonic CMS is unaware of login/logout events.
When the user logs in, this is not a problem for Enonic CMS, because the presence of a trusted header sent forward by WebSeal guarantees a valid login. However, when the user logs out, independent of Enonic CMS, this means that this header is removed/altered. In WebSeal’s case, the value of the header is changed to “Unauthenticated”.
To solve this we implement validateCurrentUser(), as this makes it possible to match the header value with the current user's username.
As this method is evaluated at every page request, it is strongly recommended to keep this method as lightweight as possible!
So let’s get started.
Create the test classes
Ok, we will implement 5 test methods.
For setting up the http request, we use the MockHttpServletRequest from the Spring mock framework. With this mock request we can simulate the http header that we expect WebSeal to pass on.
Here are the tests.
getAuthenticatedUser
Tests the HttpAutoLoginPlugin with a valid username - we expect the username to be returned, since it is valid.
getAuthenticatedUserWithIgnoredUser
When WebSeal passes on un-authenticated requests, e.g. user has not logged in, instead of sending a empty header or not setting the header at all, WebSeal passes on “Unauthenticated”.
So to handle this situation we will code our plugin to handle these special cases. A list of special usernames that should be ignored will be configured in the HttpAutoLoginPlugin configuration.
This will make the plugin generic for all header-value SSO-identification.
This test assures that these special/reserved usernames are handled correctly.
getAuthenticatedUserWithNoHeaderKey
The plugin need to know which key to use to lookup the header
validateCurrentUserWithValidUser
If the header value equals the currently logged in user, this should return true
validateCurrentUserWithInvalidUser
The header value is now reset to anonymous, so this should return false
See attached file for the complete testcode
Attachment file
SSOPluginTutorial44.zip (52 KB)
Create the plugin classes
Create the plugin classes
Ok, so we have created the test classes. Now we need to create the plugin class.
Important stuff for the HttpAutoLoginPlugin:
The HttpAutoLoginPlugin class needs to extend com.enonic.cms.api.plugin.HttpAutoLoginPlugin and implement the following
- public String getAuthenticatedUser(final HttpServletRequest request)
- public boolean validateCurrentUser( String currentUser, String userstoreName, HttpServletRequest request )
getAuthenticatedUser: When there is a valid http header passed in, identifying the user, just return this value. This will login the user into Enonic CMS.
In all other cases, return “null”.
validateCurrentUser: Perform a check to see if header value corresponds with the currently logged in user
Here are the two methods listed:
See attached file for the complete plugin code
public String getAuthenticatedUser(final HttpServletRequest request) {
if (headerLookupKey == null || headerLookupKey.equals("")) {
throw new IllegalStateException(
"Unable to find user as header value: Header key for lookup is NULL");
}
String user = request.getHeader(headerLookupKey);
if (user != null && !user.equals("")) {
if (ignores != null && ignores.size() > 0) {
for (String ignore : ignores) {
if (user.trim().equalsIgnoreCase(ignore.trim())) {
return null;
}
}
}
return user;
}
return null;
}
public boolean validateCurrentUser( String currentUser, String userstoreName, HttpServletRequest request )
{
String user = request.getHeader(headerLookupKey);
return user.equalsIgnoreCase( currentUser );
}
Attachment file
SSOPluginTutorial44.zip (52 KB)
Creating the configuration
Define the HttpAutoLoginPlugin in a file called context.xml.
Put this file under /META-INF/spring before building the jar.
Please see attachment for a complete exampl:
/src/main/resources/META-INF/spring/context.xml
Attachment file
SSOPluginTutorial44.zip (52 KB)
Deploying the plugin
Run mvn package to create the jar file. Now that you have a jar file, we can deploy it to the server.
The jar file must be placed under the $CMS_HOME/plugins directory. Restart the application and the plugins will be available.
You can go to the front page of Enonic CMS to check what kind of plugins where loaded.
Attachment file
SSOPluginTutorial44.zip (52 KB)
Using the plugin
To test the plugin on a live site, open up your website in Firefox.
(the website must be able to differentiate between logged-in/logged-out states - i.e. display logged-in-state if user is logged in).
If you haven’t already installed it, install the “Modify headers” add-on. (https://addons.mozilla.org/en-US/firefox/addon/967).
This will make you able to set the iv-user header in your browser and test the different scenarios.
Things to test:
- Set iv-user to valid username (must be present i Enonic CMS userstore) - the user should automatically be logged in
- Set iv-user to unauthenticad - the user should be logged out.
- Set iv-user back to valid user, forcing a login, the try to remove iv-user header completely. The user should again be logged out.
- Play around!
Attachment file
SSOPluginTutorial44.zip (52 KB)




Comments
21 August 2009 13:45
Commented by Sebjørn Sæther Birkeland
Where are the attached files for this article?
If you want to comment on this article you need to be logged in.