Newsletter sign-up
View all newsletters

Enterprise Java Newsletter
Stay up to date on the latest tutorials and Java community news posted on JavaWorld

Sponsored Links

Optimize with a SATA RAID Storage Solution
Range of capacities as low as $1250 per TB. Ideal if you currently rely on servers/disks/JBODs

Add the power of asynchronous processing to your JSPs

Create custom JSP tags to use with JMS

  • Print
  • Feedback

Page 5 of 5

  1. JMS does not specify a standard method for obtaining a queue connection factory from a JMS provider. Actually, JMS recommends that JMS providers allow the use of JNDI to gain access. Many JMS providers do not follow that recommendation yet and, as a result, most clients are forced to use provider-specific code to obtain the connection factory. I did not want that provider-specific code in the tags themselves. JMSQueueConnectionFactory isolates the code and, as I will discuss in the enhancements section, you can easily configure that class to allow portability across different JMS providers.
  2. JMS specifies that obtaining a queue connection to a JMS provider may be expensive, both in terms of time and resources. That probably holds true for a majority of providers. As a result, some sort of caching of connections is prudent. The JMSQueueConnectionFactory class does that for you.


Also, I decided to make JMSQueueConnectionFactory a servlet for the following reasons:

  1. I can instruct a Web server such as Tomcat to automatically load the servlet at startup. That ensures that the queue connection is ready when the JSP page using the custom tags needs it.
  2. The Web server provides me with deterministic destruction by guaranteeing to call the destroy() method during shutdown (unless the Web server crashes).
  3. The JSP content developer does not have to perform any extra initialization or cleanup work.
  4. The custom tags do not have to complete any extra initialization or cleanup work.


The JMSQueueConnectionFactory servlet is straightforward. The Web server calls the init() method at startup, during which the servlet receives the queue connection factory and uses it to obtain and cache a queue connection as shown below:

   public void init(ServletConfig config) throws ServletException
   {
      super.init(config);
      try
      {
         fiorano.jms.rtl.FioranoInitialContext ic = null;
         ic = new fiorano.jms.rtl.FioranoInitialContext();
         ic.bind ();                                      
         QueueConnectionFactory queueConnectionFactory = (QueueConnectionFactory)ic.lookup("primaryqcf");
         ic.dispose();
        JMSQueueConnectionFactory.connection = queueConnectionFactory.createQueueConnection();
        JMSQueueConnectionFactory.connection.start();
        JMSQueueConnectionFactory.lockCount = new MyInteger();
        shuttingDown = false;
      }
      .
      .
      .


Note that the code here is specific to Fiorano's FioranoMQ, which is the JMS provider that I use.

Just before the Web server shuts down, it calls the destroy() method, which will close the queue connection to ensure proper cleanup. That servlet will never invoke, so the service() method throws a RuntimeException.

Finally, the servlet has two static methods, getConnection() and releaseConnection(); the custom tags use these methods to obtain and release a queue connection, respectively. The same queue connection is reused and returned to all callers, and a simple reference-counting mechanism prevents the servlet's premature destruction. The same connection can be returned to all callers because a JMS connection object is thread-safe, i.e., it allows multithreaded access. I have a similar servlet for topic connections called the JMSTopicConnectionFactory.

Listings 4 and 5 show the complete implementation of those servlets.

Listing 4: JMSTopicConnectionFactory

Listing 5: JMSQueueConnectionFactory

Step 3: Test it out

To use the custom JSP tags created here, you will need a Web server that supports JSP 1.1. I generally use Tomcat 3.1, as it is a great Web server, and the price is right. I have created three JSP files, which you will need to actually use the custom tags. Test.jsp tests the point-to-point capability, while Test2.jsp and Test3.jsp together test the publish-and-subscribe capability of the JMS provider -- in this case FioranoMQ. If you point your browser to use Test2.jsp, it will hang until you run Test3.jsp in another browser because Test2.jsp is waiting for a message that Test3.jsp publishes. You can run Test2.jsp in multiple browsers, and all of them will receive the message published by Test3.jsp.

The JMSQueueConnectionFactory and JMSTopicConnectionFactory, servlets, and all the test JSP files are available for download in Resources. Simply download and copy a directory called javaworld under your Web apps directory. Start Tomcat and point your browser to http://localhost:8080/javaworld/Test.jsp. Remember you will also need to download and install Fiorano's FioranoMQ to run those programs. Plus you'll have to create any queues and/or topics that you use in your JSP code. In my case, for example, I created a queue called ModiQueue and a topic called ModiTopic. Fiorano's administration tool facilitates that process.

Enhancements

The tags presented here provide the basic JMS functionality you need to get your feet wet. You can add enhancements such as the ones described below to increase the capability of those tags:

  1. Message producers -- message senders and publishers -- have control over many message characteristics in JMS. Those characteristics include the message time-to-live that determines how long a message -- if not delivered -- stays around until it is dropped, the priority of the message, and whether the message persists in permanent storage (at least more permanent than RAM). For simplicity, the custom tags introduced in this article do not control those characteristics. However, it is not difficult to expose those characteristics as attributes of the write tag similar to the destination attribute.
  2. JMS defines the concept of a transaction in both the point-to-point and publish-and-subscribe messaging models. Any application that deals with transferring data that should not be corrupted or lost should always do so under the umbrella of a transaction. As a result, both the write and read tags should be enhanced to optionally use a transaction if specified.
  3. The JMSQueueConnectionFactory and JMSTopicConnectionFactory classes contain JMS provider-specific code. Therefore, swapping out providers requires some coding. With some more design work, a properties file/XML file that allows new providers to be easily used can make those classes configurable. In essence, the provider-specific code is pulled out into yet another class, which has a well-defined interface (as defined by you). The properties file informs the JMSQueueConnectionFactory or JMSTopicConnectionFactory of which of those classes to use to obtain the connection factory. That is essentially the strategy pattern.



Conclusion

By using JSP content, developers can create powerful and dynamic Webpages and applications. When coupled with JMS, JSP becomes even more robust. Because the JSP architects have given us the strength of extending JMS with custom tags, using JMS with JSP is not difficult.

The next time you need to update an inventory database halfway across the world from your JSP page, and you don't want your JSP page to wait 30 minutes for the update to finish, don't worry. Just use the custom JSP tags that I created in this article, and welcome to the wonderful world of asynchronous programming with JMS!

About the author

Tarak Modi is an independent consultant and a certified Java programmer. He has a master's degree in computer engineering and an MBA concentrating in information systems. He has several years of proven experience working with C++, Java, and technologies such as DCOM, CORBA, RMI, and EJB. He has written articles for leading software magazines including JavaWorld and is currently working on a book on JMS with Manning Publications from which this article has been adapted. To find out more about the book visit http://www.manning.com/modi/index.html. Also, visit Tarak's home page: http://tmodi.home.att.net/.

Read more about Enterprise Java in JavaWorld's Enterprise Java section.

  • Print
  • Feedback

Resources