Archive for the ‘J2EE’ Category

For the REST-purists under us, a resources ending with a slash is not the same as a resource ending without a slash. However, the difference between url://xxxx.com/a and url://xxxx.com/a/ is ignored. The trailing slash is omitted.

When you try to map a resource with a trailing slash using the standard @Path annotation, the methods get mapped to the same endpoint causing an exception.

@RequestScoped
public class TestResource {

 @Path("{path}")
 @GET
 public String test1(@PathParam("path") String path) {
 return "test1";
 }

 @Path("{path}/")
 @GET
 public String test2(@PathParam("path") String path) {
 return "test2";
 }
}

Glassfish answers during the deployment with:

SEVERE: Following issues have been detected: WARNING: A resource model has ambiguous (sub-)resource method for HTTP method GET and input mime-types as defined by @Consumes and @Produces annotations at Java methods … These two methods produces and consumes exactly the same mime-types and therefore their invocation as a resource methods will always fail.

In Glassfish which uses the Jersey under the hood, the slash is also ignored. But there is a workaround. You can use regex in the Path-annotation to map resources ending with a slash. In the example at the end, I use regex to map the paths to the methods. But there is something you should know about the path-matching algorithm. The mapping algorithm uses the following rules:

The JAX-RS specification has defined strict sorting and precedence rules for matching URI expressions and is based on a most specific match wins algorithm. The JAX-RS provider gathers up the set of deployed URI expressions and sorts them based on the following logic:

  1. The primary key of the sort is the number of literal characters in the full URI matching pattern. The sort is in descending order.
  2. The secondary key of the sort is the number of template expressions embedded within the pattern, i.e., {id} or {id : .+}. This sort is in descending order.
  3. The tertiary key of the sort is the number of nondefault template expressions. A default template expression is one that does not define a regular expression, i.e., {id}.

In the following example,  test2 is found before test1 because the regex is longer! We check the trailing slash first. When it fails, it falls back to test1.


@RequestScoped
public class TestResource {

 @Path("{test:.*}")
 @GET
 public String test1(@PathParam("test") String test) {
 return "test1";
 }

 @Path("{test:.*[/]}") // takes precedence
 @GET
 public String test2(@PathParam("test") String test) {
 return "test2";
 }
}

Advertisement

For one of my customers, we needed a very simple workflow-framework which coordinates the flow between methods inside a J2EE6 application on Glassfish. The business required to implement the following simple logic:

  1. Create a job.
  2. When step 1 was successful, then start a job (which affects some thousand objects) and send an email
  3. End a job when step 2 was successfull.
  4. Mark the job as failed when one of the steps couldn’t be completed due to the implemented business-logic.
  5. Provide a handler to handle exceptions.

Taking a fully fledged workflow-system was way over the top to solve this problem. The workflow will also remain unchanged; and when it is changed, the code needed to be altered to. We needed to come up with a simple workflow-management which is bound to transitions and methods.

So, first we decided to create an observer the change the transitions of the workflow-steps. This is basically a very simple method which alters the status and stores it in the database. The next step was to create some annotations to add to the methods which needed to be executed during a certain step. We annotate our workflow methods as follows:

@Asynchronous
@TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
@Workflow
@WorkflowStep(from = Status.IDLE, to = Status.PROGRESS)
public void startJob(@WorkflowActionHandler
                     @Observes(notifyObserver = Reception.ALWAYS,
                               during = TransactionPhase.AFTER_SUCCESS)
                     final JobWorkflowEvent event) {}

This straight-forward approach is very clean and simple. Basically it says that this method will be executed after the transition from a Status.IDLE to Status.PROGRESS. Although we use an enum here, you could take any arbitrary integer. Using the CDI annotations we get some additional power. This method will only be executed after the success of the previous step. Here you can combine the full power of CDI with some basic workflow concepts to create a nice system.

Now remains the problem of the transition handling. The transitions are handled in an interceptor which is marked by the @Workflow annotation.

@Interceptor 
@Workflow
public class WorkflowInterceptor {

}

This interceptor does not do much more than changing the transition state when the method pinged by CDI has the correct workflow-steps. It uses some reflection to figure that out and allows access to the method.

To handle exceptions, we introduce a new annotation:

@Asynchronous
@TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
@Workflow 
@WorkflowException
public void excJob(@WorkflowActionHandler 
                   @Observes(notifyObserver = Reception.ALWAYS,
                             during = TransactionPhase.AFTER_FAILURE)
                   final JobWorkflowEvent event) {
}

Whenever one step fails unexpected, control is transferred to this method where certain actions can be executed. We need this annotation to prevent other methods to pick this event up. 

Using CDI together with some custom annotations really did the job and works fine.

Well, as you might have expected from the title, the answer is “yeah well, not really”. A singleton in the J2EE world is not a singleton as you know it from the normal Java world. In a non-J2EE environment you typically write something like this to generate a singleton:

public class MySingleton {
  final private static MySingleton instance = new MySingleton();

  protected String name = "whatever";

  private MySingleton() {}

  public static MySingleton instance() {
    return instance;
  }
}

You can get exactly one instance of this bean and you could access the fields directly or through getter and setters. There is only one instance of this object and all information is stored there. This pattern is well known to every programmer. The demand was great to port this pattern to the J2EE world. A new type of bean was invented, the Singleton bean. The idea behind all this is to provide a single instance of a particular bean within your application. You can construct a singleton bean with the following code:

@LocalBean
@Singleton
@Startup
public class MySingleton {

}

First we declare it as a local bean, and we load it during startup. The @Singleton annotation makes a singleton out of this class. But is this class really instantiated once when using the @LocalBean annotation? No, it is instantiated twice! Let’s test this out with by adding a static field in the bean.

static int i=1;</pre>
public MySingleton() {
    System.out.println("INSTANCE: " + i++);
}

You will see in the logs that you get two different instances. If you print out the reference of the class, you will notice that one of the instances is a proxy object. The proxy object is instantiated too and the constructor is instantiated again. When you write some kind of initialisation logic inside the constructor, you will run into somekind of unwanted behaviour because it executes your code twice where you expect that the constructor is executed only once. So, don’t use the constructor to set up your data but use the @PostConstruct annotation to execute a method with your initialisation logic in it.

@PostConstruct
public void init() {
   ... do your init here ....
}

You will see that the proxy object does not execute this code (which is obvious of course because the code is not in the constructor anymore). Another pitfall might be that during some kind of rapid prototyping action you store some state-data in a non-private field in the singleton or a stateful session bean. When you do not provide a getter/setter for the field, the field-value of the injected bean will always be null because the proxy gets injected and not the “real” instance. The proxy object does not store state. Let’s test this:

@LocalBean
@Singleton
@Startup
public class MySingleton {
    protected String name = "whatever";
    .....
    public String getName() {
         return this.name;
    }
}

We inject this bean in another session:

@LocalBean
@Stateless
public class MyTest {
    @EJB private MySingleton mySingleton;

    public void test() {
        // mySingleton.name --&gt; null; (proxy)
        // mySingleton.getName() ---&gt; "whatever" (real object)
    }
}

The injected reference is the proxy object without state. Getting the value of the field directly must always return null when it is not initialised. The real state is maintained in the singleton. You can get the “real” data when you use the method “getName()” because the proxy object tunnels your method and not the field. This is the reason behind the fact that you may not use fields directly in session-beans.

Well, as you might have expected, it is really a bad idea to get the field from a singleton or other bean directly (in general, it is an anti-pattern in J2EE). Try to encapsulate your data with nice getters and setters and keep in mind that your objects can get dynamic proxies depending on the annotations you add to the class.