Home JBoss Server JBoss MDB 3.0
11 | 03 | 2010
JBoss 5 AS Book
"JBoss AS 5 development" reviews
Please share your feedback/review with other readers!
Banner
Dashboard
Advertise with Us
Banner
RSS Feed
Login
Sign here for the NewsLetter.



Poll
What book could be in your wish list next XMas ?
 
JBoss admin resources
Banner
JBoss howto

How can you solve deployment errors caused by large war/jar/ear files ?

jboss recipe of the day ...
Read More

How do you configure your .war to be deployed after your EJB ?

jboss recipe of the day ...
Read More

How do I configure a Queue/Topic to work in a cluster?

JBoss recipe of the day ...
Read More
JBoss MDB 3.0 PDF Print E-mail
Written by Mark S.   
Thursday, 25 September 2008 14:00
Message-driven beans (MDBs) are stateless, server-side, transaction-aware components for processing asynchronous JMS messages. Introduced since EJB 2.0, message-driven beans process messages delivered via the Java Message Service.
Message-driven beans can receive JMS messages and process them using the same robust component-based infrastructure that session and entity beans enjoy. While a message-driven bean is responsible for processing messages, its container takes care of automatically managing the component’s entire environment including transactions, security, resources, concurrency, message
acknowledgment, etc.
One of the most important aspects of message-driven beans is that they can consume and process messages concurrently. This capability provides a significant advantage over traditional JMS clients, which must be custom-built to manage resources, transactions, and security in a multi-threaded environment.

Before the release 3.0 of EJB also MDB needed a configuration file describing its properties, now let's see an example of MDB using annotations. it turns out that writing an MDB is just a matter of a few minutes:

package com.sample;

import javax.ejb.ActivationConfigProperty;
import javax.ejb.MessageDriven;
import javax.jms.Message;
import javax.jms.MessageListener;

@MessageDriven(name = "MessageMDBSample", activationConfig = {
        @ActivationConfigProperty(propertyName = "destinationType", propertyValue = "javax.jms.Queue"),
        @ActivationConfigProperty(propertyName = "destination", propertyValue = "queue/MyQueue"),
        @ActivationConfigProperty(propertyName = "acknowledgeMode", propertyValue = "Auto-acknowledge") })

public class DummyMDBean implements MessageListener {

    @Resource
    private MessageDrivenContext context;

    @Resource(name = "OracleDS")
    public void setDataSource(DataSource dataSource) {
        this.dataSource = dataSource;
    }
    
    @PostConstruct
    public void initialize() {
        try {
            connection = dataSource.getConnection();
        } catch (SQLException sqle) {
            sqle.printStackTrace();
        }
    }

    @PreDestroy
    public void cleanup() {
        try {
            connection.close();
            connection = null;
        } catch (SQLException sqle) {
            sqle.printStackTrace();
        }
    }



    public void onMessage(Message message) {

        try {
            Statement statement = connection.createStatement();
            statement.execute("INSERT INTO ...........");
        } catch (JMSException jmse) {
            jmse.printStackTrace();
            context.setRollBackOnly();
        } catch (SQLException sqle) {
            sqle.printStackTrace();
            context.setRollBackOnly();
        }

    }

}

MDB 3.0 Annotations


the @MessageDriven annotation identifies this object as an MDB and specifies the MDB configuration,
the activationConfig property of the message driven annotation lets you provide messaging-system specific configuration information through an array of ActivationConfigProperty instances. 

@MessageDriven(name = "MessageMDBSample", activationConfig = {
       @ActivationConfigProperty(propertyName = "destinationType", propertyValue = "javax.jms.Queue"),
        @ActivationConfigProperty(propertyName = "destination", propertyValue = "queue/MyQueue"),
      @ActivationConfigProperty(propertyName = "acknowledgeMode", propertyValue = "Auto-acknowledge") })


In our case we define the destionationType of our MDB as Queue listening on the "queue/MyQueue".
Last property is the acknowledge Mode  which is set to Auto-acknowledge.

Other EJB 3.0 Annotations


Besides MDB annotations here you can see an interesting example of Resource injection: when the
MDB is initialized a DataSource is injected  using the following setter method:

    @Resource(name = "OracleDS")
    public void setDataSource(DataSource dataSource) {
        this.dataSource = dataSource;
    }


The connection will be then used to insert data in the onMessage method (here we don't use a DAO
just to keep the example very simple and short).
We need as well to inject a MessageDrivenContext context in order to rollback the transaction in case
of error.

That's all. With this simple class you can manage asynchronously your transactions, without even
the need for a configuration file.

Packaging your MDB:


packaging your mdb is simply a matter of putting the .class file in a jar archive, that's all !

$ jar cvf mdbExample.jar com


An MDB client:

We add here a simple servlet client which you might use to test your MDB: pack your servlet in a war
file, your ejb in a jar file and put everything in an ear archive.

package com.sample.servlet;

import java.io.*;
import java.util.*;
import javax.jms.*;
import javax.jms.Queue;
import javax.naming.*;
import javax.servlet.*;
import javax.servlet.http.*;

public class testJMS extends HttpServlet {

Context context = null;
QueueConnection queueConnection = null;
QueueSession queueSession = null;
Queue queue = null;
QueueSender queueSender = null;
TextMessage message = null;
boolean esito = true;

public void init() {
       

      try {
           context = new InitialContext();
           getQueueSender();
           context.close();
           } catch(Exception exc) {
           System.out.println(exc.toString());
           esito = false;
      }
}


public void getQueueSender() throws JMSException,NamingException {

    QueueConnectionFactory queueFactory = (QueueConnectionFactory)context.lookup("ConnectionFactory");
        queueConnection = queueFactory.createQueueConnection();
        queueSession = queueConnection.createQueueSession(false,
             javax.jms.Session.AUTO_ACKNOWLEDGE);
        queue = (Queue)context.lookup("queue/MyQueue");
        queueSender = queueSession.createSender(queue);
        message = queueSession.createTextMessage();
}

public void sendMsg(String testo) throws JMSException {
     message.setText(testo);
     queueSender.send(queue, message);
}

public void doGet(HttpServletRequest request, HttpServletResponse response) throws IOException,
                               ServletException {
      String whereToForward = null;
      String testo = request.getParameter("text");
      if (text==null) {
          text="dummy message";
      }
        if(esito) {
                    try {
                          sendMsg(text);
                          whereToForward = "success";
                          } catch (JMSException jme) {
                          System.out.println(jme.toString());
                     whereToForward = "failure";
                     }
         } else {
                   whereToForward = "failure";
         }
        System.out.println("Done!");
       
}

public void destroy() {
       try {
            if(queueSender != null)queueSender.close();
            } catch (JMSException jme) {
            System.out.println(jme.toString());
            } finally {
            queueSender = null;
      }
      try {
           if(queueSession != null)queueSession.close();
           } catch (JMSException jme) {
           System.out.println(jme.toString());
           } finally {
           queueSession = null;
      }
      try {
           if(queueConnection != null)queueConnection.close();
           } catch (JMSException jme) {
           System.out.println(jme.toString());
           } finally {
           queueConnection = null;
           }
      }
} 



JBoss.org Search
Custom Search
Comments
Search
muhilan  - How to set up this example   |2008-10-15 16:11:58
Hi
I am new to JBoss and writing MDBs as well. But I have learnt the
fundamentals of JMS and would like to go further by installing, running and
playing with this sample.
Could I have instructions on setting up the sample
application provided by you above?

thanks for the help
Muhilan
F.Marchioni   |2008-10-21 09:19:08
Hello muhilan,
basically start with an IDE that compiles java classes,
f.e. Eclipse.
Create a new Java project, then create a Java class
named "DummyMDBean".
Cut and paste the class from the sample
in it.
Add the libraries jboss-ejb3x.jar (which is under server\default\lib),
jboss-annotations-ejb3.jar, jbossall-client.jar (which are under \client).
Now compile this class and jar
it.

Deploy it to the server.

Note: you need two resources for
this sample: a JMS queue named "queue/MyQueue" and a
DataSource whose JNDI name is "OracleDS". (But if you want you can
skip this last one just remove the @Resource annotation)
muhilan  - do you a ready to deploy ear for now?   |2008-10-21 16:57:04
Hi
I am in the process of creating a project in Eclipse and deploying it to
JBoss. Meanwhile I would also like to try out a packaged version of your example
application, if you have it.
Thanks in advance
Muhilan
muhilan  - Do I need an ejb-jar.xml?   |2008-10-21 16:43:06
Many thanks for your reply. I probably do not need an ejb-jar.xml, but would I
need it in this case?
What directory structure do you recommend for creating an
eclipse project?
muhilan  - tried another sample as well   |2008-10-21 16:51:48
I have a sample ear that I developed based on the instructions given
in:**********.testwww.netbeans.org/kb/55/ejb30-jbo ss.html
But Netbeans packages
it in a different way, I was not able to get the sample running. According to
the the page, it should work. I keep getting exceptions whenever I try to
deploy.
I have tried the JBoss forums, with no luck. I would appreciate it, if
you can give me some insight on why my ear file does not deploy.
Thanks
F.Marchioni   |2008-10-21 16:57:36
right, you don't need an ejb-jar.xml in this case.
The structure of an EJB 3.0
project is quite simple so just put your EJB into the src folder of Eclipse.

Personally I use a simple ant script that picks up the ejb classes jar them
and insert the jar into the ear (If I need an ear file).
have a nice day
Anonymous  - re: tried another sample as well   |2008-10-21 16:59:42
muhilan wrote:
I have a sample ear that I developed based on the instructions
given in:**********.testwww.netbeans.org/kb/55/ejb30-jbo ss.html
But
Netbeans packages it in a different way, I was not able to get the sample
running. According to the the page, it should work. I keep getting
exceptions whenever I try to deploy.
I have tried the JBoss forums, with
no luck. I would appreciate it, if you can give me some insight on why
my ear file does not deploy.
Thanks

What kind of error have you got when deployin ?
muhilan  - org.xml.sax.SAXException: Element Type "messaging   |2008-10-21 17:12:39
The error I am getting is (with the ejb-jar.xml and even without
it!!)

../server/default/deploy/MyEar.ear -> org.xml.sax.SAXException: Element
Type: messaging-type must be declared, and I have messaging-type in my
ejb-jar.xml
muhilan  - created an EJB 3.0 project   |2008-10-21 17:41:06
The imports are not working still, and I have not found
jboss-annotations-ejb3.jar. I have 40 errors in my project
F.Marchioni   |2008-10-21 17:50:43
so if you have errors at first fix the imports. Pick up
jboss-annotations-ejb3.jar from JBOSS_HOME/client/.

One more thing : these
jars are necessary only for compiling the EJB, verify that your jar doesn't
contain any of these jars otherwise they will conflict with those installed on
jBoss
muhilan  - some errors resolved   |2008-10-21 17:49:44
I added jboss-javaee.jar and the errors on the import statement went away. Looks
like I am making some progress at least. But errors remain
Only registered users can write comments!

3.26 Copyright (C) 2008 Compojoom.com / Copyright (C) 2007 Alain Georgette / Copyright (C) 2006 Frantisek Hliva. All rights reserved."

Last Updated ( Monday, 06 October 2008 19:51 )