Tuesday, March 26, 2013

Java EE 7 and EJB 3.2 support in JBoss AS 8

 Update (June 10 2013): JBoss AS is now known as WildFly. This post was written before WildFly 8.0.0.Alpha1 was released. Any references to JBoss AS8 in this article should be considered as a reference to WildFly 8. Read my next article here http://jaitechwriteups.blogspot.in/2013/06/wildfly-release-and-history-behind-the-release.html which explains what WildFly is and why JBoss AS was renamed to WildFly.

Some of you might be aware that the Public Final Draft version of Java EE 7 spec has been released. Among various other new things, this version of Java EE, brings in EJB 3.2 version of the EJB specification. EJB 3.2 has some new features compared to the EJB 3.1 spec. I'm quoting here the text present in the EJB 3.2 spec summarizing what's new:

The Enterprise JavaBeans 3.2 architecture extends Enterprise JavaBeans to include the following new functionality and simplifications to the earlier EJB APIs:
  • Support for the following features has been made optional in this release and their description is moved to a separate EJB Optional Features document:
    • EJB 2.1 and earlier Entity Bean Component Contract for Container-Managed Persistence
    • EJB 2.1 and earlier Entity Bean Component Contract for Bean-Managed Persistence
    • Client View of an EJB 2.1 and earlier Entity Bean
    • EJB QL: Query Language for Container-Managed Persistence Query Methods
    • JAX-RPC Based Web Service Endpoints
    • JAX-RPC Web Service Client View

  • Added support for local asynchronous session bean invocations and non-persistent EJB Timer Service to EJB 3.2 Lite.

  • Removed restriction on obtaining the current class loader; replaced ‘must not’ with ‘should exercise caution’ when using the Java I/O package.

  • Added an option for the lifecycle callback interceptor methods of stateful session beans to be executed in a transaction context determined by the lifecycle callback method's transaction attribute.

  • Added an option to disable passivation of stateful session beans.

  • Extended the TimerService API to query all active timers in the same EJB module.

  • Removed restrictions on javax.ejb.Timer and javax.ejb.TimerHandle references to be used only inside a bean.

  • Relaxed default rules for designating implemented interfaces for a session bean as local or as remote business interfaces.

  • Enhanced the list of standard activation properties.

  • Enhanced embeddable EJBContainer by implementing AutoClosable interface.

As can be seen, some of the changes proposed are minor. But there are some which are useful major changes. We'll have a look at a couple of such changes in this article.

1) New API TimerService.getAllTimers()

EJB 3.2 version introduces a new method on the javax.ejb.TimerService interface, named getAllTimers. Previously the TimerService interface had (and still has) a getTimers method. The getTimers method was expected to return the active timers that are applicable for the bean on whose TimerService, the method had been invoked (remember: there's one TimerService per EJB).

In this new EJB 3.2 version, the newly added getAllTimers() method is expected to return all the active timers that are applicable to *all beans within the same EJB module*. Typically, an EJB module corresponds to a EJB jar, but it could also be a .war deployment if the EJBs are packaged within the .war. This new getAllTimers() method is a convenience API for user applications which need to find all the active timers within the EJB module to which that bean belongs.

2) Ability to disable passivation of stateful beans

Those familiar with EJBs will know that the EJB container provides passivation (storing the state of the stateful bean to some secondary store) and activation (loading the saved state of the stateful bean) capability to stateful beans. However, previous EJB versions didn't have a portable way of disabling passivation of stateful beans, if the user application desired to do that. The new EJB 3.2 version introduces a way where the user application can decide whether the stateful bean can be passivated or not.

By default, the stateful bean is considered to be "passivation capable" (like older versions of EJB). However, if the user wants to disable passivation support for certain stateful bean, then the user has the option to either disable it via annotation or via the ejb-jar.xml deployment descriptor.

Doing it the annotation way is as simple as setting the passivationCapable attribute on the @javax.ejb.Stateful annotation to false. Something like:

 @javax.ejb.Stateful(passivationCapable=false) // the passivationCapable attribute takes a boolean value  
 public class MyStatefulBean {  

Doing it in the ejb-jar.xml is as follows:

 <?xml version="1.0" encoding="UTF-8"?>  
 <ejb-jar xmlns="http://xmlns.jcp.org/xml/ns/javaee"  
       <!-- passivation-capable element takes either a true or a false value -->  

Two important things to note in that ejb-jar.xml are the version=3.2 attribute (along with the http://xmlns.jcp.org/xml/ns/javaee/ejb-jar_3_2.xsd schema location) on the ejb-jar root element and the passivation-capable element under the session element.

So, using either of these approaches will allow you to disable passivation on stateful beans, if you want to do so.

Java EE 7 and EJB 3.2 support in JBoss AS8:

JBoss AS8 has been adding support for Java EE 7 since the Public Final Draft version of the spec has been announced. Support for EJB 3.2 is already added and made available. Some other Java EE 7 changes have also made it to the latest JBoss AS 8 builds. To keep track of the Java EE 7 changes in JBoss AS8, keep an eye on this JIRA https://issues.jboss.org/browse/AS7-6553.

To use the already implemented features of Java EE 7 in general or EJB 3.2 in particular, you can download the latest nightly build/binary of JBoss AS from here. Give it a try and let us know how it goes. For any feedback, questions or if you run into any kind of issues, feel free to open a discussion thread in our user forum here.


Aka aka said...

Featurewise this is some seriously underwhelming release. Did the EG really spend 3 years on this?

The small changes are welcome and moving some of the EJB 2 stuff to the optional part is great, but after 3 years I think people expect just a little more than this.

Jaikiran said...

The changes I blogged were very specific to EJB 3.2 which is just a minor part of the Java EE 7 features. The entire feature set of Java EE 7 is much more and the EE 7 spec will have more details. But you can see a brief glimpse of what's new in EE 7 in this JIRA here https://issues.jboss.org/browse/AS7-6553

Aka aka said...

I actually meant that EJB 3.2 is underwhelming.

Java EE 7 has some great additions, but why did it take the EJB 3.2 EG some 3 years to come up with some very small features, some clarifications, and a pruning that was really started in Java EE 6?

Fernando Rubbo said...

Are you going to add container interceptors in ejb 3.2? For me, this is a must have feature

Jaikiran said...

Fernando, "container interceptors" https://docs.jboss.org/author/display/AS72/Container+interceptors which is a JBoss AS specific feature isn't part of the EJB 3.2 spec nor of any Java EE spec.

For it to be part of the specification, the use case will have to be raised with the relevant EG (interceptors EG in this case) so that it can be discussed with various application server implementors. Would you be willing to open a discussion in the user mailing list here http://java.net/projects/interceptors-spec/lists/users/archive/2013-03 explaining your use case?

Unknown said...

@Aka aka

The EJB EG is by nature of its process a conservative one.

I tried to push for an alternate approach, but that was ran into a catch-22 (so to speak :-) ).

Now out of the ~100 issues raised, 70 got resolved. I'm curious which issue (raised before draft deadlines) are you specifically missing?


Abhijit Sarkar said...

I know I'm commenting on an "old" article but one problem that I'm finding is that there're no samples available for the Wildfly specific deployment desciptors. For example, what'd be the schema declarations for jboss-ejb3.xml? Just changing the schema from java.sun.com to xmlns.jcp.org isn't valid.