Search code examples
javajmsmq

find the queue depth of MQ


I want to find the current queue depth of MQ. My program can read and write on queue.

I am able to write a consumer to consume message from queue. I can use counter to count how many messages were in queue. But I need to find the queue depth without loosing the messages.

try {
        // Create a connection factory
        JmsFactoryFactory ff = JmsFactoryFactory.getInstance(WMQConstants.WMQ_PROVIDER);
        JmsConnectionFactory cf = ff.createConnectionFactory();

        // Set the properties
        cf.setStringProperty(WMQConstants.WMQ_HOST_NAME, HOST);
        cf.setIntProperty(WMQConstants.WMQ_PORT, PORT);
        cf.setStringProperty(WMQConstants.WMQ_CHANNEL, CHANNEL);
        cf.setIntProperty(WMQConstants.WMQ_CONNECTION_MODE, WMQConstants.WMQ_CM_CLIENT);
        cf.setStringProperty(WMQConstants.WMQ_QUEUE_MANAGER, QMGR);
        cf.setStringProperty(WMQConstants.WMQ_APPLICATIONNAME, "JmsPutGet (JMS)");
        cf.setBooleanProperty(WMQConstants.USER_AUTHENTICATION_MQCSP, true);
        cf.setStringProperty(WMQConstants.USERID, APP_USER);
        cf.setStringProperty(WMQConstants.PASSWORD, APP_PASSWORD);

        // Create JMS objects
        context = cf.createContext();
        destination = context.createQueue("queue:///" + QUEUE_NAME);

        long uniqueNumber = System.currentTimeMillis() % 1000;
        TextMessage message = context.createTextMessage("Your lucky number today is " + uniqueNumber);

        producer = context.createProducer();
        producer.send(destination, message);
        System.out.println("Sent message:\n" + message);

        consumer = context.createConsumer(destination); // autoclosable
        String receivedMessage = consumer.receiveBody(String.class, 15000); // in ms or 15 seconds

        System.out.println("\nReceived message:\n" + receivedMessage);

        recordSuccess();
    }

The code should print the queue depth.


Solution

  • Queue depth can be counted by browsing messages. Browsing does not consume messages.

    Connection connection = connectionFactory.createConnection();
    connection.start();
    
    Session session = connection.createSession(false, Session.DUPS_OK_ACKNOWLEDGE);
    Queue q = session.createQueue("exampe_queue");
    QueueBrowser browser = session.createBrowser(q);
    Enumeration enumeration = browser.getEnumeration();
    
    long msgCounter = 0;
    while (enumeration.hasMoreElements()) {
        Message msg = (Message) enumeration.nextElement();
        msgCounter += 1;
    }
    
    System.out.println("Queue depth: " + msgCounter);
    

    However this method is very slow as client is pulling messages from broker. It will work if you need to check your queue depth sporadically for monitoring purpose or similar.

    Better solution would be to use get-me-a-q-depth call but this is not specified by JMS api; however it is usually present in the implementation specific library.