Jul 262010
 

If you have followed my Eclipse / GlassFish / Java EE 6 Cookbook, you have seen one single section, where the sample code was only sketched and never compiled. This was the “hypothetical security interceptor”. And of course when one writes down code from memory, it is invariably buggy.

Last week I wanted to use the code as base of the security interceptor of a system that we just develop, naturally it crashed, and it did so in a not exactly obvious way, thus I thought I should give you an update.

The security interceptor as shown in the cookbook is not really what I would use anyway, and I intend to write a follow-up tutorial explaining some of the things that I learned during our current project. There you will find a more detailed discussion of access control, and along with it, a more useful SecurityInterceptor.

Until that point, let me show you what the problem with the original code was. Here it is:

@Interceptor
@Stateless
public class SecurityInterceptor {
 
    @EJB SecurityEao sec;
    @EJB SecurityGuard guard;
 
    @AroundInvoke
    public Object intercept(InvocationContext ctx) throws Exception {
 
        Map<String, Object> contextData = ctx.getContextData();
        Map<String, String> headers = contextData.get("javax.xml.ws.http.request.headers");
 
        String secKey = headers.get("X-Portal-SecKey");
        if (secKey == null) {
            throw new SecurityNoKeyException();
        }
        SecInfo secInfo = eao.secInfoBySecKey(secKey);
        Method invokedMethod = ctx.getMethod();
        if (guard.isInvocationForbidden(invokedMethod, secInfo)) {
            throw new SecurityViolationException();
        }
        return ctx.proceed();
    }
}

The wrong assumption is that contextData.get("javax.xml.ws.http.request.headers"); yields a Map<String, String>. That’s wrong, but it compiles. The method really yields a Map<String, List<String>>, because you can have more than one header of a certain name. Thus the correct code is something like

@Interceptor
@Stateless
public class SecurityInterceptor {
 
    @EJB SecurityEao sec;
    @EJB SecurityGuard guard;
 
    @SuppressWarnings("unchecked")
    @AroundInvoke
    public Object intercept(InvocationContext ctx) throws Exception {
 
        Map<String, Object> contextData = ctx.getContextData();
        Map<String, List<String>> headers 
             = (Map<String, List<String>>) contextData.get("javax.xml.ws.http.request.headers");
 
        List<String> secCredentials = headers.get("X-Portal-Credentials");
        if (secCredentials == null || secCredentials.isEmpty()) {
            throw new SecurityNoCredentialsException();
        }
        SecInfo secInfo = sec.secInfoBySecCredentials(secCredentials);
        Method invokedMethod = ctx.getMethod();
        if (!guard.isInvocationAllowed(invokedMethod, secInfo)) {
            throw new SecurityViolationException();
        }
        return ctx.proceed();
    }
}

I have already updated the tutorial.

Apr 062010
 

Version 1.4, last updated May 23, 2011 – 11:10

The content of this tutorial is still relevant, but you may also consider my new open source Azzyzt JEE Tools, a set of Eclipse plugins that greatly simplify the process of creating a Java Enterprise application using the patterns outlined in this tutorial. See the Azzyzt JEE Tools home page and especially the tutorial “Using Azzyzt JEE Tools“.

In “4 – Equipment” I have committed myself to using Eclipse and the Java Enterprise Edition as my tools, while in “5 – Patterns And Languages” I’ve declared my high-level goals for implementing a next step of design pattern-based tools. Now, for a deeper understanding of design patterns, you first have to use them. This post in the form of a tutorial shows some very basic project setups using Eclipse and GlassFish.

I am no expert in this field, some important things may be missing, so just take the following as a set of things that work for me.

As I am not immune to learning, and as I am going the use these things a lot, it is inevitable that my understanding of certain aspects will change. I suppose that means, I will have to make changes to this post whenever it happens. If I ever do so, I will post a short notice.

Applicability

This is a tutorial about using Eclipse and the GlassFish v3 Java application server to implement Java EE 6 applications. I will show how to use different Eclipse project types for different purposes, will show how to do manual tests and how to implement automatic unit tests. We will not create a complete application, but more a vertical slice through an application. The idea is to just touch all relevant areas, not to finish a project.

The tutorial assumes the existence of a relational database, and it concentrates on the Java application used as a backend. Using JSF or another server-based GUI framework is definitely out of scope.

Where’s the beef?

At an equivalent of approximately 80 printed pages, the full tutorial is much too long for a regular blog post. It would break the size limit of feeds syndicated via Google’s Feedburner server. In fact it did. I had no choice but to move the text to a separate page. On the other hand, that’s quite OK, I want my tutorials (this won’t be the last) to be available as pages from a tutorial menu anyway.

Unfortunately I noticed the feed problems only after I had already published the URL of this post a few times. Thus, if you arrive here from a link, please go on to the actual page containing the full Eclipse / GlassFish / Java EE 6 tutorial. Sorry for the inconvenience.