activemq-artemis/examples/jms/pre-acknowledge
jbertram e6a3d3a0c5 ACTIVEMQ6-14 Replace JNDI server with client impl 2014-12-05 09:27:52 -06:00
..
src/main ACTIVEMQ6-14 Replace JNDI server with client impl 2014-12-05 09:27:52 -06:00
pom.xml ACTIVEMQ6-14 Replace JNDI server with client impl 2014-12-05 09:27:52 -06:00
readme.html Remove references to HornetQ in doc and Comments 2014-11-19 15:15:35 +00:00

readme.html

<html>
  <head>
    <title>ActiveMQ JMS Pre-Acknowledge Example</title>
    <link rel="stylesheet" type="text/css" href="../common/common.css" />
    <link rel="stylesheet" type="text/css" href="../common/prettify.css" />
    <script type="text/javascript" src="../common/prettify.js"></script>
  </head>
  <body onload="prettyPrint()">
     <h1>JMS Pre-Acknowledge Example</h1>

     <p>Standard JMS supports three acknowledgement modes: AUTO_ACKNOWLEDGE, CLIENT_ACKNOWLEDGE, and
     DUPS_OK_ACKNOWLEDGE. For a full description on these modes please consult the JMS specification, or any
     JMS tutorial.</p>
     <p>All of these standard modes involve sending acknowledgements from the client to the server. However
     in some cases, you really don't mind losing messages in event of failure, so it would make sense
     to acknowledge the message on the server <b>before</b> delivering it to the client.</p>
     <p>By acknowledging the message before sending to the client, you can avoid extra network traffic and CPU
     work done in sending acknowledgements from client to server.</p>
     <p>The down-side of acknowledging on the server before delivery, is that if the system crashes after acknowledging
     the message, but before the message has been received by the client, then, on recovery, that message
     will be lost. This makes pre-acknowledgement not appropriate for all use cases, but it is very useful for some
     use-cases when you can cope with such loss of messages<p>
     <p>An example of a use-case where it might be a good idea to use pre-acknowledge, is for stock price update
     messages. With these messages it might be ok to lose a message in event of crash, since the next price
     update message will arrive soon, overriding the previous price.</p>
     <p>In order to use pre-acknowledge functionality with ActiveMQ the session has to be created with
     a special, ActiveMQ specific acknowledgement mode, given by the value of
     <code>ActiveMQJMSConstants.PRE_ACKNOWLEDGE</code>.     
     <h2>Example step-by-step</h2>
     <p><i>To run the example, simply type <code>mvn verify</code> from this directory</i></p>

     <ol>
        <li>Create an initial context to perform the JNDI lookup.</li>
        <pre class="prettyprint">
           <code>
     initialContext = getContext(0);
     </code>
        </pre>

        <li>Perform the look-ups</li>
        <pre class="prettyprint">
           <code>
     Queue queue = (Queue)initialContext.lookup("/queue/exampleQueue");

     ConnectionFactory cf = (ConnectionFactory)initialContext.lookup("/ConnectionFactory");                      
           </code>
        </pre>

        <li>Create a the JMS objects.</li>
        <pre class="prettyprint">
           <code>
     connection = cf.createConnection();

     Session session = connection.createSession(false, ActiveMQSession.PRE_ACKNOWLEDGE);

     MessageProducer producer = session.createProducer(queue);
         
     MessageConsumer messageConsumer = session.createConsumer(queue);           
           </code>
        </pre>

        <li>Create and send a message.</li>
        <pre class="prettyprint">
           <code>
     TextMessage message1 = session.createTextMessage("This is a text message 1");

     producer.send(message1);

     System.out.println("Sent message: " + message1.getText());           
           </code>
        </pre>

        <li>Print out the message count of the queue. The queue contains one message as expected
        delivery has not yet started on the queue.</li>
        <pre class="prettyprint">
           <code>
     int count = getMessageCount(connection);
       
     System.out.println("Queue message count is " + count);           
           </code>
        </pre>

        <li>Start the Connection, delivery will now start. Give a little time for delivery to occur.</li>
        <pre class="prettyprint">
          <code>
     connection.start();

     Thread.sleep(1000);          
          </code>
       </pre>

        <li>Print out the message count of the queue. It should now be zero, since the message has
         already been acknowledged even before the consumer has received it.</li>         
        <pre class="prettyprint">
           <code>
     count = getMessageCount(connection);         
     
     System.out.println("Queue message count is now " + count);
           </code>
        </pre>

        <li>Finally, receive the message.</li>
        <pre class="prettyprint">
           <code>
     TextMessage messageReceived = (TextMessage)messageConsumer.receive(5000);

     System.out.println("Received message: " + messageReceived.getText());           
           </code>
        </pre>

        <li>Be sure to close our resources!</li>
          <pre class="prettyprint">
           <code>
     if (initialContext != null)
     {
        initialContext.close();
     }
     if (connection != null)
     {
        connection.close();
     }           
           </code>
        </pre>
     </ol>
     
     <h2>More information</h2>
     
     <ul>
         <li>User Manual's <a href="../../../docs/user-manual/en/html_single/index.html#pre-acknowledge">Pre-acknowledgement Mode chapter</a></li>
     </ul>
     
  </body>
</html>