Package openjms.examples.client.console

Source Code of openjms.examples.client.console.SimpleConsumer

/**
* Redistribution and use of this software and associated documentation
* ("Software"), with or without modification, are permitted provided
* that the following conditions are met:
*
* 1. Redistributions of source code must retain copyright
*    statements and notices.  Redistributions must also contain a
*    copy of this document.
*
* 2. Redistributions in binary form must reproduce the
*    above copyright notice, this list of conditions and the
*    following disclaimer in the documentation and/or other
*    materials provided with the distribution.
*
* 3. The name "Exolab" must not be used to endorse or promote
*    products derived from this Software without prior written
*    permission of Exoffice Technologies.  For written permission,
*    please contact info@exolab.org.
*
* 4. Products derived from this Software may not be called "Exolab"
*    nor may "Exolab" appear in their names without prior written
*    permission of Exoffice Technologies. Exolab is a registered
*    trademark of Exoffice Technologies.
*
* 5. Due credit should be given to the Exolab Project
*    (http://www.exolab.org/).
*
* THIS SOFTWARE IS PROVIDED BY EXOFFICE TECHNOLOGIES AND CONTRIBUTORS
* ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT
* NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL
* EXOFFICE TECHNOLOGIES OR ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
* INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
* OF THE POSSIBILITY OF SUCH DAMAGE.
*
* Copyright 1999 (C) Exoffice Technologies Inc. All Rights Reserved.
*
* $Id: SimpleConsumer.java,v 1.40 2002/03/12 11:57:31 jima Exp $
*
* Date         Author  Changes
* 04/25/2000   jima    Created
*/
package openjms.examples.client.console;

import java.io.PrintStream;
import java.util.Hashtable;
import javax.naming.InitialContext;
import javax.naming.Context;
import javax.jms.DeliveryMode;
import javax.jms.Session;
import javax.jms.TopicConnectionFactory;
import javax.jms.TopicConnection;
import javax.jms.TopicSession;
import javax.jms.TopicSubscriber;
import javax.jms.MessageListener;
import javax.jms.Message;
import javax.jms.Topic;
import javax.jms.TextMessage;
import javax.jms.TopicConnectionFactory;
import javax.jms.JMSException;
import javax.jms.ExceptionListener;
import org.exolab.jms.util.CommandLine;
import org.exolab.core.logger.LoggerFactory;
import org.exolab.core.logger.LoggerIfc;
import org.exolab.core.logger.LogEventType;
import org.exolab.jms.client.JmsTopicConnectionFactory;
import org.exolab.jms.jndi.JndiConstants;
import org.exolab.jms.jndi.rmi.RmiJndiInitialContextFactory;

/**
* The simple consumer is used to subscribe to a particular topic and receive
* events. It will set a message listener so that events can be pushed down
* to it when they become available.
*/
public class SimpleConsumer
    implements MessageListener, TimerListener, ExceptionListener {
    public SimpleConsumer(String name, TopicConnection connection,
        TopicSubscriber subscriber, int ackMode, int seconds, boolean summary) {
        this(name, connection, subscriber, ackMode, false, 0, seconds, summary);
    }

    public SimpleConsumer(String name, TopicConnection connection,
        TopicSubscriber subscriber, int ackMode, int count, int seconds, boolean summary) {
        this(name, connection, subscriber, ackMode, true, count, seconds, summary);
    }

    private SimpleConsumer(String name, TopicConnection connection,
        TopicSubscriber subscriber, int ackMode,
        boolean counting, int count, int seconds, boolean summary) {
        name_ = name;
        connection_ = connection;
        subscriber_ = subscriber;
        ackMode_ = ackMode;
        counting_ = counting;
        count_ = count;
        seconds_ = seconds;
        summary_ = summary;
        timer_ = new Timer(this, seconds_ * 1000);
        timer_.start();
        received_ = 0;
    }

    static public void main(String[] args) {
        try {
            CommandLine cmdline = new CommandLine(args);

            if (cmdline.exists("help")) {
                // the help option has been specified, print the usage
                // information
                usage();
            } else if (cmdline.exists("topic")) {
                // see if an ack mode has been specified. If it hasn't
                // then assume CLIENT_ACKNOWLEDGE mode.
                int ackMode = Session.CLIENT_ACKNOWLEDGE;
                if (cmdline.exists("ackmode")) {
                    String amode = cmdline.value("ackmode");
                    if (amode.equals("auto")) {
                        ackMode = Session.AUTO_ACKNOWLEDGE;
                    } else if (amode.equals("dups")) {
                        ackMode = Session.DUPS_OK_ACKNOWLEDGE;
                    } else if (!amode.equals("client")) {
                        // ignore all ack modes, to test no acking
                        ackMode = -1;
                    }
                }

                // enable debugging - undocumented option
                if (cmdline.exists("debug")) {
                    LoggerIfc logger = LoggerFactory.getLogger();
                    logger.setLogLevel(LogEventType.Debug);
                }

                String topic_name = cmdline.value("topic");
                if (topic_name != null) {
                    // connect to the JNDI server and get a reference to
                    // root context
                    Hashtable props = new Hashtable();
                    String host = "localhost";
                    String port = null;
                    String jndiname = "JndiServer";

                    String mode = "rmi";
                    if (cmdline.exists("mode")) {
                        mode = cmdline.value("mode");
                    }

                    String modeType =
                        RmiJndiInitialContextFactory.class.getName();

                    if (cmdline.exists("jndiport")) {
                        port = cmdline.value("jndiport");
                    }

                    if (cmdline.exists("jndihost")) {
                        host = cmdline.value("jndihost");
                    }

                    // override the default server name if specified on the
                    // command line.
                    if (cmdline.exists("jndiname")) {
                        jndiname = cmdline.value("jndiname");
                    }

                    if (mode.equals("ipc") || mode.equals("tcp")) {
                        if (port == null) {
                            port = "3035";
                        }

                        props.put(Context.PROVIDER_URL,
                            "tcp://" + host + ":" + port + "/");
                        modeType =
                            "org.exolab.jms.jndi.mipc.IpcJndiInitialContextFactory";
                    } else if (mode.equals("http")) {
                        System.out.println("Using HTTP");

                        /* CONNECTING BY WAY OF PROXY 
                           Client needs to set these system properties if
                           it requires to go through a proxy for HTTP.
                           System.setProperty("http.proxyHost", host);
                           System.setProperty("http.proxyPort", port);
                        */

                        /* CONNECTING FOR SSL TRANSACTIONS.
                           Client needs to set these system properties
                           if it requires to go through a proxy for
                           HTTPS.

                           System.setProperty("https.proxyHost", "host");
                           System.setProperty("https.proxyPort", "port");
                          

                           Client needs to pass in "-mode http -secure"
                           to use https,
                           Client needs -Djavax.net.ssl.trustStore=cacerts
                           passed in. JSSE is required to make this work.
                        */
                        String type = "http://";

                        if (cmdline.exists("secure")) {
                            if (port == null) {
                                port = "8443";
                            }
                            type = "https://";
                            modeType =
                                "org.exolab.jms.jndi.http.SslHttpJndiInitialContextFactory";
                        } else {
                            if (port == null) {
                                port = "8080";
                            }
                            modeType =
                                "org.exolab.jms.jndi.http.HttpJndiInitialContextFactory";
                        }

                        props.put(Context.PROVIDER_URL,
                            type + host + ":" + port + "/" +
                            "openjms/servlet/OpenJMSJndi");
                        String url = cmdline.value("url");
                        if (url == null) {
                            if (cmdline.exists("secure")) {
                                url = type + "localhost:8443";
                            } else {
                                url = type + "localhost:8080";
                            }
                        }

                        // Client URL to allow server to send messages
                        // to registered consumers/receivers
                        System.getProperties().setProperty
                            (JndiConstants.HTTP_CLIENT_URL_PROPERTY, url);

                    } else {
                        if (port == null) {
                            port = "1099";
                        }

                        props.put(Context.PROVIDER_URL,
                            "rmi://" + host + ":" + port + "/" + jndiname);
                    }

                    System.err.println("Using provider url " + props.get(Context.PROVIDER_URL));
                    props.put(Context.INITIAL_CONTEXT_FACTORY, modeType);
                    Context context = new InitialContext(props);

                    // lookup the connection factory from the context
                    TopicConnectionFactory factory = (TopicConnectionFactory)
                    context.lookup("JmsTopicConnectionFactory");

                    // if we can't find the factory then throw an exception
                    if (factory == null) {
                        throw new RuntimeException(
                            "Failed to locate connection factory");
                    }

                    LoggerFactory.getLogger().logDebug("Have the connection factory " + factory);
                    TopicConnection connection =
                        factory.createTopicConnection();

                    TopicSession session =
                        connection.createTopicSession(false, ackMode);

                    Topic topic = null;
                    if (cmdline.exists("persistent")) {
                        topic = (Topic)context.lookup(topic_name);
                    } else {
                        topic = session.createTopic(topic_name);
                    }

                    if (topic == null) {
                        System.err.println("Failed to get administered object"
                            + " exiting.....");
                        System.exit(-1);
                    }

                    String selector = null;
                    if (cmdline.exists("selector")) {
                        selector = "JMSPriority=1";
                    }

                    // determine if the summary flag has been specified. By
                    // default the message details are printed out. If the
                    // summary flag is specified then the count of the messages
                    // received is displayed.
                    boolean summary = false;
                    if (cmdline.exists("summary")) {
                        summary = true;
                    }

                    // if the 'name' option has been specified then assume a
                    // durable subscriber otherwise transient
                    TopicSubscriber subscriber = null;
                    String name = cmdline.value("name");
                    if (name != null) {

                        subscriber = session.createDurableSubscriber
                            (topic, name, selector, false);
                    } else {
                        subscriber = session.createSubscriber(topic, selector, false);
                    }

                    int secs = 60;
                    boolean counted = false;
                    int count = 1;

                    if (cmdline.exists("count")) {
                        counted = true;
                        try {
                            String value = cmdline.value("count");
                            count = Integer.parseInt(value);
                        } catch (Exception exception) {
                            System.err.println("Illegal count value");
                            System.exit(-1);
                        }
                    }

                    // the timeout is used to terminate the consumer if not
                    // messags are received within the specified timeframe.
                    // The default value is 5 minutes.
                    secs = 5 * 60;
                    if (cmdline.exists("timeout")) {
                        secs = Integer.parseInt(cmdline.value("timeout"));
                    }

                    SimpleConsumer consumer = (counted)
                    ? new SimpleConsumer(name, connection, subscriber, ackMode, count, secs,summary)
                    : new SimpleConsumer(name, connection, subscriber, ackMode, secs, summary);
                    subscriber.setMessageListener(consumer);
                    connection.setExceptionListener(consumer);

                    // start the connection unless the noStart option is specified
                    if (!cmdline.exists("noStart")) {
                        connection.start();
                    }

                } else {
                    System.err.println("Cannot subscribe to messages under "
                        + "null topic");
                }
            } else {
                // anything else print the usage message
                usage();
            }
        } catch (Exception exception) {
            exception.printStackTrace();
            System.err.println("Fatal error: " + exception + "\nExiting.....");
            System.exit(-1);
        }
    }

    /**
     * All messages that for this consumer are pumped down to this method
     *
     * @param       message             message to retrieve
     */
    public void onMessage(Message message) {
        String mode = "unknown";
        String id = "unset";
        int priority = -1;

        if (!summary_) {
            System.err.print(message + ", ");
        }
       
        try {
            if (message.getJMSDeliveryMode() == DeliveryMode.NON_PERSISTENT) {
                mode = "NON_PERSISTENT";
            } else if (message.getJMSDeliveryMode() == DeliveryMode.PERSISTENT) {
                mode = "PERSISTENT";
            }
        } catch (JMSException ignore) {
        }

        try {
            id = message.getJMSMessageID();
            priority = message.getJMSPriority();
        } catch (JMSException ignore) {
            // ignore the exception.
        }

        // only print the details if the summary flag is not specified
        if (!summary_) {
            System.err.println("JMSDeliveryMode=" + mode + ", Priority=" +
                priority + ", JMSMessageID=" + id);
        }

        // timer_.reset();

        try {
            if (ackMode_ == Session.CLIENT_ACKNOWLEDGE) {
                message.acknowledge();
            }
        } catch (JMSException exception) {
            System.err.println("Failed  in ack message " + exception);
        }

        if (counting_ && ++received_ >= count_) {
            try {
                // can't do the close in the same thread as the callback.
                // therefore reset the message listener and set the timer
                // to do the exist and clean up in another thread. Doing
                // a close in the same thread can cause a lockup
                subscriber_.setMessageListener(null);


                // display a summary of the messages received
                if (summary_) {
                    System.err.println("The consumer " + name_ + " received " +
                                       received_ + " messages from topic " + subscriber_.getTopic());
                }
               
                // kill the timer
                timer_.stop();
                exit("");
            } catch (JMSException exception) {
                System.err.println("Could not unset the listener " + exception);
            }
        }
    }

    public void onTimeout() {
        exit("No message received in the last " + seconds_ +
            " seconds, exiting");
    }

    // implementation of ExceptionListener.onException
    public void onException(JMSException exception) {
        exit("Received onException notification");
    }

   
    private void exit(String message) {

        if (!summary_) {
            System.err.println(message);
        }
        try {
            connection_.close();
            timer_.stop();
        } catch (Exception error) {
            System.exit(0);
            error.printStackTrace();
        }
    }
   
    /**
     * Print out information on running this sevice
     */
    static protected void usage() {
        PrintStream out = System.out;

        out.println("usage: java " + SimpleConsumer.class.getName() +
            " [options]\n");
        out.println("options:");
        out.println("  -topic <name>      topic to subscribe to.\n");
        out.println("  -name <consumer>   durable consumer name.\n");
        out.println("  -mode <ipc | rmi | http>  " +
            "connect using ipc, http or rmi mode. " +
            "Defaults to 'rmi'.\n");
        out.println("  -url <url> only used for http mode, the client passes\n"
            "              this url to the server, to allow the server\n"
            "              to invoke the clients servlet at the\n"
            "              specfified url. Defaults to "
            "'http://localhost:8080'.\n");
        out.println("  -secure only used for http mode. Connect using https.\n"
            "   requires JSSE jars, https enabled Web server etc.\n");
        out.println("  -ackmode <auto | client | dups>\n" +
            "                     message acknowledgement mode. " +
            "Defaults to 'client'.\n");
        out.println("  -persistent        " +
            "specifies persistent delivery mode.\n");
        out.println("  -jndiport <num>    port where the jndi server runs.\n");
        out.println("  -jndihost <host>   host where jndi server runs.\n");
        out.println("  -jndiname <name>   name of the jndi server\n");
        out.println("  -count <num>       number of messages to wait for.\n");
        out.println("  -timeout <seconds> seconds to wait before exiting.\n");
        out.println("  -help              displays this screen.\n");
    }  


    private String name_;
    private TopicSubscriber subscriber_;
    private TopicConnection connection_;
    private int ackMode_;
    private Timer timer_;
    private int seconds_;
    private boolean counting_;
    private int count_;
    private int received_;
    private boolean summary_;
}
TOP

Related Classes of openjms.examples.client.console.SimpleConsumer

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.