Inside Scoop on J2EE : Tips and tricks on J2EE and Oracle Application Server by Debu Panda
Updated: 3/28/2006; 4:34:07 AM.

 

Subscribe to "Inside Scoop on J2EE" in Radio UserLand.

Click to see the XML version of this web page.

Click here to send an email to the editor of this weblog.

 
 

Thursday, April 15, 2004

EJB Timer Service – A Close Look

 

Introduction

The EJB 2.1 specification introduced a new feature that allows transactional, time-based event notifications. In this article we will discuss how can you use the Timer functionality to use to schedule business activity. We will take an Entity bean as an example and demonstrate what you have to do to create a timer and use this in a J2EE container like OC4J to schedule a recurring task that occur at a regular interval. Also we will discuss the benefits and limitations of the Timer service and take a look how Oracle has extended the EJB Timer functionality to support cron timers.

What is a Timer Service?

The EJB Timer is a service managed by EJB Container to allow EJB methods to register to call back at a schedule time. Essentially the EJB Timers provides facilities like crontab process of UNIX world to schedule. The Timer could be a single-event Timer that can occur at a specific time or after a specific elapsed duration or an interval timer that may occur at specific intervals.

 For example, you can use the timer service can be used do one of the following:

  • Run an attendance report after every 8 hours after completion of a job shift 
  • Cleanup a temporary database table  at the end of the day
  • Update the employee table from a remote location every week

Let’s assume that you have to implement a business activity that needs to be invoked at a regular interval after 30 mts.

Using a Timer Service

 

You can use Timer Service with all types of EJBs except Stateful EJBs. The TimerService is accessed by an EJB via its EJBContext. A timer created by an entity bean is associated with the identity of bean instance.

In order to use a Timer service you have to do the following:

  • The EJB bean class must implement javax.ejb.TimedObject
  • Create a method in the EJB bean class to invoke and create the timer object. Expose the method in the remote/local interface of the EJB. This method will be called by the clients to intialize the timer.
  • Implement the ejbTimeOut() method to perform the business logic when the timer is expired

 

In this example, we have a requirement to have a business activity occur at a regular interval of time so we need to create an interval timer. You have to use the createTimer() method to create the Timer. As we want to create an interval timer that expires after regular interval we will pass the initial expiration time and the interval as parameters. Please note that the interval is specified in milliseconds.

 

In my EJB, I have a method named initializeTimer() that creates the Timer service to be invoked by the client that occurs after a regular interval after a specified time.

 

 

public void initializeTimer(Date firstDate, long timeout, String info) throws RemoteException

  {

    try {

      TimerService ts = ctx.getTimerService();

      ts.createTimer(firstDate, timeout, info);

      System.out.println("Timer created at " + new Date(System.currentTimeMillis()) +

                   " with a timeout: " + timeout + " and with info: " + info);

      System.out.println(" Collection info : " + ts.getTimers());

 

    } catch (Exception e) {

     

            System.out.println("Exception after create timer : "+ e.toString());

 

    }

    return;

  }

 

Implement the Business Logic

 

You have to implement the business logic in the ejbTimeout() method  of the EJB as follows in my example:

 

public void ejbTimeout(Timer timer)

  {

                 

    System.out.println("ejbTimeout() called at: " + new Date(System.currentTimeMillis()) +

                  " with info: " + timer.getInfo());

    System.out.println("Generating Report”);

 

    return;

  }

 

Initializing the Timer Service

 

You have to call the intializeTimer() method of the EJB in your client to initialize the timer service. You probably do want to hardcode the initial expiration time and interval in your applications and either pass as a parameter from your deployment descriptors or supplied by the users according to the business requirement. 

 

     

     

// create employee bean

Employee rec = (Employee) home.create(empNo, empName, salary);

System.out.println("Employee bean Created for empNo:"+empNo +"<br>");

// Set up timers - param in millisec

Date firstDate = new java.util.Date();

rec.initializeTimer(firstDate, timerDuration, timerName);

 

 

You have to pass the value for Date as java.util.Date, timeDuration as milliseconds so you have to pass 1800000 if you want your business process to execute after every 30mts.

 

When the application will execute this code, this will create the timer service and the container will invoke the call the ejbTimeout() method at the required interval.

 

Full source code for a sample application that uses a Timer with entity bean is available for download at Oracle Technology Network at http://otn.oracle.com/tech/java/oc4j/1003/how_to/how-to-ejb-timer.zip.

 

Benefits of Timer service

 

1) J2EE standard and supported

 

EJB Timers are part of J2EE standard and will be supported all application server vendors and your application will be portable across containers. Also you do not worry about extra configuration that is required for an external Timer service/job scheduler like Quartz.

 

2) Container Managed

Timer is a container managed service and you do not worry about a separate thread pools/user threads that are required from an external scheduler.

 

3) Transactions Support

 

Transactions are fully supported with Timers. Normally timers are created within a scope of transaction and hence timer is cancelled when transaction is rolled back. You would like to specify the transaction attribute for the ejbTimeout() method as follows:

 

<container-transaction>

         <method>

            <ejb-name>EmployeeBean</ejb-name>

            <method-name>ejbTimeout</method-name>

         </method>

         <trans-attribute>RequiresNew</trans-attribute>

      </container-transaction>

4) Timer Persistence

 

Timers are persisted and survive EJB life cycles and container crash.

 

 

4) Timer Clustering

 

Vendors are coming up implementations that will make Timers highly available. Oracle plans to support for clustering support fof Timers in a future release of Oracle Application Server.

 

 

 

Limitations of Timer Service

 

1)      These are coarse-grained service and may not be suitable for real-time events.

2)      Lacks support for cron based a timer that is popular.

3)      EJB Timer is a part of J2EE 1.4 and there is no production application server from leading vendors like Oracle, BEA and IBM and that has J2EE 1.4 support.

 

 

CRON Timers with EJBs – A possibility with vendor extensions

 

In the UNIX world, you can schedule a timer to execute regularly at specified intervals known as cron timers. Unfortunately EJB specification does not support cron Timers. However some vendors like Oracle has extended their EJB containers to support cron timers with EJBs. You can use cron expressions for scheduling Timer events with EJBs with OracleAS containers for J2EE (OC4J) 10.0.3.

 

Some examples of cron expressions are as follows:

 

0 8 4 7 * ---> The fourth of July at 8:00 A.M.

15 10 * * 15 ---> Every Friday at 10:15 A.M.

 

If you want to use cron Timers with EJB you have to use Oracle specific APIs to create the Timer.  You have to pass the cron expression as a parameter to the parameter to the createTimer method.

 

Following is the code example that depicts the use of CRON timers with EJB:

 

import oracle.ias.container.timer.EJBTimer;

import oracle.ias.container.timer.EJBTimerService;

...

String cronExpr = "0 8 4 7 * ";

EJBTimerService ets = (EJBTimerService) ctx.getTimerService();

EJBTimer et = ets.createTimer(cronExpr, info);

 

The cron EJBTimer service in OC4J can also specify an arbitrary Java class that can be scheduled to be invoked when a cron timer expires. Here is code example that demonstrates scheduling of an arbitrary Java class

 

EJBTimerService ets = (EJBTimerService) ctx.getTimerService();

EJBTimer et = ets.createTimer(cronExpr,"mypackage.MyTimerClass", info);

 

For arbitrary Java classes, the info variable can be either null or be a String[] of parameters to pass to the main method of the class.

 

You must provide a main method within the mypackage.MyTimerClass, which is used as

The entry point, as follows:

 

public static void main( String args[] )

 

 

 

Conclusion

EJB Timers are very useful and can be used to schedule business activity that need be invoked at a specified time or at regular interval. Timer Service inherits all benefits of EJBs like container support for transactions, persistence, etc.

 

References and further reading

1) EJB 2.1 specification at http://java.sun.com/j2ee/

2) EJB 2.1 The Timer Service by Richard Monson-Haefel  at http://www.theserverside.com/articles/article.tss?l=MonsonHaefel-Column4


4:24:32 AM    comment []

© Copyright 2006 Debu Panda.

PS: These are my own thoughts and not of my employer ..



Click here to visit the Radio UserLand website.
 


April 2004
Sun Mon Tue Wed Thu Fri Sat
        1 2 3
4 5 6 7 8 9 10
11 12 13 14 15 16 17
18 19 20 21 22 23 24
25 26 27 28 29 30  
Mar   May