Fedora 24 Released

Fedora Project Contributors has just released Fedora v24.
https://fedoraproject.org/wiki/Releases/24/ChangeSet

Fedora is a Linux-based operating system, a suite of software that makes your computer run. You can use the Fedora operating system to replace or to run alongside of other operating systems such as Microsoft Windows or Mac OS X. The Fedora operating system is 100% free of cost for you to enjoy and share.

Regards,
Roger Lacroix
Capitalware Inc.

Linux, Open Source, Operating Systems Leave a comment

Another Sample Java/MQ Program – MQWrite2

Someone over at Stack Overflow posted a question about logging MQ error messages to a file. After the user updated the posting, I recognized the code as mine (MQWrite.java) that I wrote back in 2000 (Yup, 16 years ago!!).

So, I decided to bring MQWrite.java into this decade and created MQWrite2.java. Here is MQWrite2.java that sets the connection information in a HashTable and uses Log4J as the logger. (You can download it from here.)

import java.io.IOException;
import java.util.Hashtable;

import org.apache.log4j.Logger;

import com.ibm.mq.MQException;
import com.ibm.mq.MQMessage;
import com.ibm.mq.MQPutMessageOptions;
import com.ibm.mq.MQQueue;
import com.ibm.mq.MQQueueManager;
import com.ibm.mq.constants.CMQC;

/**
 * Program Name
 *  MQWrite2
 *
 * Description
 *  This java class will connect to a queue manager and
 *  and write a message to a queue.
*
 * Sample Command Line Parameters
 *  -h 127.0.0.1 -p 1414 -c TEST.CHL -m MQA1 -q TEST.Q1
 *
 * @author Roger Lacroix, Capitalware Inc.
 */
public class MQWrite2
{
   private Logger logger = Logger.getLogger(MQWrite2.class.getName());
   private Hashtable<String, String> params = null;
   private Hashtable<String, Object> mqht = null;
   private String qMgrName;
   private String outputQName;

   /**
    * The constructor
    */
   public MQWrite2()
   {
      super();
      logger.info("MQWrite2 is now starting.");
   }

   /**
    * Make sure the required parameters are present.
    * @return true/false
    */
   private boolean allParamsPresent()
   {
      boolean b = params.containsKey("-h") && params.containsKey("-p") &&
                  params.containsKey("-c") && params.containsKey("-m") &&
                  params.containsKey("-q");
      if (b)
      {
         try
         {
            Integer.parseInt((String) params.get("-p"));
         }
         catch (NumberFormatException e)
         {
            b = false;
         }
      }

      return b;
   }

   /**
    * Extract the command-line parameters and initialize the MQ variables.
    * @param args
    * @throws IllegalArgumentException
    */
   private void init(String[] args) throws IllegalArgumentException
   {
      params = new Hashtable<String, String>();
      if (args.length > 0 && (args.length % 2) == 0)
      {
         for (int i = 0; i < args.length; i += 2)
         {
            params.put(args[i], args[i + 1]);
         }
      }
      else
      {
         throw new IllegalArgumentException();
      }

      if (allParamsPresent())
      {
         qMgrName = (String) params.get("-m");
         outputQName = (String) params.get("-q");

         mqht = new Hashtable<String, Object>();

         mqht.put(CMQC.CHANNEL_PROPERTY, params.get("-c"));
         mqht.put(CMQC.HOST_NAME_PROPERTY, params.get("-h"));

         try
         {
            mqht.put(CMQC.PORT_PROPERTY, new Integer(params.get("-p")));
         }
         catch (NumberFormatException e)
         {
            mqht.put(CMQC.PORT_PROPERTY, new Integer(1414));
         }

         // I don't want to see MQ exceptions at the console.
         MQException.log = null;
      }
      else
      {
         throw new IllegalArgumentException();
      }
   }

   /**
    * Connect, open queue, write a message, close queue and disconnect.
    *
    */
   private void testReceive()
   {
      int openOptions = CMQC.MQOO_OUTPUT + CMQC.MQOO_FAIL_IF_QUIESCING;
      MQPutMessageOptions pmo = new MQPutMessageOptions();
      MQQueueManager _qMgr = null;
      MQQueue queue = null;
      MQMessage sendMsg = null;
      String line = "This is a test message.";

      try
      {
         _qMgr = new MQQueueManager(qMgrName, mqht);
         queue = _qMgr.accessQueue(outputQName, openOptions);

         sendMsg = new MQMessage();
         sendMsg.messageId = CMQC.MQMI_NONE;
         sendMsg.correlationId = CMQC.MQCI_NONE;
         sendMsg.writeString(line);
         // put the message on the queue
         queue.put(sendMsg, pmo);
         logger.info("MQWrite2 Message inserted: " + line);
      }
      catch (MQException mqex)
      {
         logger.error("MQWrite2 MQException CC=" +mqex.completionCode + " : RC=" + mqex.reasonCode);
      }
      catch (IOException e)
      {
         logger.error("MQWrite2 IOException " + e.getLocalizedMessage());
      }
      finally
      {
         try
         {
            if (queue != null)
               queue.close();
         }
         catch (MQException mqex2)
         {
            logger.error("MQWrite2 MQException CC=" +mqex2.completionCode + " : RC=" + mqex2.reasonCode);
         }
         finally
         {
            try
            {
               if (_qMgr != null)
                  _qMgr.disconnect();
            }
            catch (MQException mqex3)
            {
               logger.error("MQWrite2 MQException CC=" +mqex3.completionCode + " : RC=" + mqex3.reasonCode);
            }
         }
      }

      logger.info("MQWrite2 is now ending.");
   }

   /**
    * main line
    * @param args
    */
   public static void main(String[] args)
   {
      MQWrite2 write = new MQWrite2();

      try
      {
         write.init(args);
         write.testReceive();
      }
      catch (IllegalArgumentException e)
      {
         System.out.println("Usage: java MQWrite2 -h host -p port -c channel -m QueueManagerName -q QueueName");
         System.exit(1);
      }

      System.exit(0);
   }
}

And here is the ‘log4j.properties’ file that goes with the code (it is included in the download):

#
# stdout
#
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern=%m%n
#
# MQWrite
#
log4j.category.MQWrite2=DEBUG, mqwrite, stdout
#log4j.category.MQWrite2=INFO, mqwrite, stdout
# "mqwrite" appender writes to a file
log4j.appender.mqwrite=org.apache.log4j.RollingFileAppender
log4j.appender.mqwrite.File=log/MQWrite.log
log4j.appender.mqwrite.MaxFileSize=1000KB
log4j.appender.mqwrite.MaxBackupIndex=9
log4j.appender.mqwrite.layout=org.apache.log4j.PatternLayout
log4j.appender.mqwrite.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss} %p - %m%n
#log4j.appender.mqwrite.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %p (%F:%M:%L) - %m%n

Make sure you create a ‘log’ directory under the directory where you run the code from or else it will throw an error like:

log4j:ERROR setFile(null,true) call failed.
java.io.FileNotFoundException: log\MQWrite.log (The system cannot find the path specified)

Regards,
Roger Lacroix
Capitalware Inc.

IBM i (OS/400), Java, Linux, Mac OS X, MQ, Programming, Unix, Windows Leave a comment

A Tip for Handling Java/MQ Internal Message Class

Here’s an interesting head-scratcher. I was writing some Java code to handle an MQ message and in this particular case, it was an MQRFH2 message. The code below was working fine until I decided to dump (output) the message in hexadecimal.

int openOptions = CMQC.MQOO_INQUIRE + CMQC.MQOO_FAIL_IF_QUIESCING;
MQGetMessageOptions gmo = new MQGetMessageOptions();
gmo.options = CMQC.MQGMO_NO_WAIT + CMQC.MQGMO_FAIL_IF_QUIESCING;
MQQueueManager _qMgr = null;
MQQueue queue = null;
MQMessage receiveMsg = null;
MQRFH2 rfh2;
byte[] b;
boolean getMore = true;

try
{
   _qMgr = new MQQueueManager(qManager);
   queue = _qMgr.accessQueue(inputQName, openOptions);

   while(getMore)
   {
      receiveMsg = new MQMessage();
      try
      {
         queue.get(receiveMsg, gmo);

         printMsgHex(receiveMsg);

         if (CMQC.MQFMT_RF_HEADER_2.equals(receiveMsg.format))
         {
            rfh2 = new MQRFH2(receiveMsg);
         }

         b = new byte[receiveMsg.getDataLength()];
         receiveMsg.readFully(b);
         System.out.println("Message data-> " + new String(b));
      }
      catch (com.ibm.mq.MQException e)
      {
         System.err.println("CC=" +e.completionCode + " : RC=" + e.reasonCode);
         getMore = false;
      }
      catch (java.io.IOException ioex)
      {
         System.err.println("ioex=" +ioex);
         getMore = false;
      }
      catch (MQDataException e)
      {
         System.err.println("CC=" +e.completionCode + " : RC=" + e.reasonCode);
         getMore = false;
      }
   }
}
catch (com.ibm.mq.MQException mqex)
{
   System.err.println("CC=" +mqex.completionCode + " : RC=" + mqex.reasonCode);
}
finally
{
   try
   {
      if (queue != null)
         queue.close();
   }
   catch (com.ibm.mq.MQException mqex2)
   {
      System.err.println("CC=" +mqex2.completionCode + " : RC=" + mqex2.reasonCode);
   }
   finally
   {
      try
      {
         if (_qMgr != null)
            _qMgr.disconnect();
      }
      catch (com.ibm.mq.MQException mqex3)
      {
         System.err.println("CC=" +mqex3.completionCode + " : RC=" + mqex3.reasonCode);
      }
   }
}

The printMsgHex() method is a simple method to retrieve the message and output.

byte[] b = new byte[msg.getMessageLength()];
msg.readFully(b);
etc...

When I would run the code, I would get the following error:

CC=2 : RC=6114

The MQ Knowledge Center says the following:

6114 (X'17E2') MQRC_INSUFFICIENT_DATA

Explanation:
There is insufficient data after the data pointer to accommodate the request. This reason code occur s in the WebSphere MQ C++ environment.

Completion Code:
MQCC_FAILED

I scratched my head and said WTF. I’m coding in Java but it is giving me a C++ error message. I commented out the printMsgHex() method and the code would work. I have used the printMsgHex() method for years. I looked at the code and nothing stood out. The only thing different about this code and the other code was the use of the MQRFH2 class.

I sat and stared at the code (we all know that works) and I could not see anything wrong with the code. As I sat scratching my head, I started thinking about the MQMessage class and it occurred to me that IBM implemented it like RandomAccessFile class. Then the light went on. I wondered if the MQRFH2 class reset the cursor position. So I added the following line before the call to the MQRFH2 class and bingo, everything started to work as expected.

receiveMsg.seek(0);

So, the bottom-line is if your code is going to mess around with the message then before using an internal message header class like MQRFH, MQRFH2, MQCIH, MQDEAD, MQIIH or MQXMIT, make sure you update the message’s cursor position to the correct location before passing the message to the class.

if (CMQC.MQFMT_RF_HEADER_2.equals(receiveMsg.format))
{
   receiveMsg.seek(0);
   rfh2 = new MQRFH2(receiveMsg);
}

Regards,
Roger Lacroix
Capitalware Inc.

IBM i (OS/400), Java, Linux, Mac OS X, MQ, Programming, Unix, Windows Leave a comment

Using SSL TLS To Connect 2 MQ Queue Managers Using Self-Signed Certificates

Angel Rivera and Mike Cregger of IBM have published a support document titled:
Using SSL TLS to connect two MQ queue managers in MQ 7.5 and MQ 8.0 / MQ 9.0 using self-signed certificates

The document provides step-by-step details for connecting a WebSphere MQ V7.5 queue manager in one platform (Windows) to a V8.0 queue manager running on another platform (Linux), using SSL TLS self-signed certificates.

Note: I have not tested the information in the document.

I have put a local link to the PDF here, in case IBM reshuffles their web site in the page disappears.

Regards,
Roger Lacroix
Capitalware Inc.

Education, Linux, MQ, Security, Unix, Windows Leave a comment

Jeff Lowrey will be Speaking at MQTC v2.0.1.6

Jeff Lowrey of IBM will be speaking at MQ Technical Conference v2.0.1.6 (MQTC).

    Jeff Lowrey’s Sessions:

  • IBM MQ and IBM IOTF MessageSight v2.0
  • IBM MQ Appliance Lab
  • IBM MQ and IBM IOTF MessageSight v2.0 Lab

For more information about MQTC, please go to:
http://www.mqtechconference.com

Regards,
Roger Lacroix
Capitalware Inc.

Capitalware, Education, MQ, MQ Technical Conference Leave a comment

MQ Labs at MQTC v2.0.1.6

Lyn Elkins of IBM and her team are generously hosting MQ Labs at MQTC v2.0.1.6. The lab will have 10-12 PCs/laptops with IBM MQ running on them. The labs will be free-format. Attendees will be able to use the lab when they have free time.

    MQ Labs:

  • Monday 8:30AM to 5:00PM in Booth 7 (next to the Aloeswood room)
  • Tuesday 8:30AM to 12:00PM (noon) in Booth 7 (next to the Aloeswood room)

For more information about MQTC, please go to:
http://www.mqtechconference.com

Regards,
Roger Lacroix
Capitalware Inc.

Capitalware, Education, MQ, MQ Technical Conference Leave a comment

Bill Karounos will be Speaking at MQTC

Bill Karounos will be presenting the following session at MQ Technical Conference v2.0.1.6 (MQTC):

    Bill Karounos’s Technical Session:

  • What’s New in IBM Integration Bus v10

For more information about MQTC, please go to:
http://www.mqtechconference.com

Regards,
Roger Lacroix
Capitalware Inc.

Capitalware, Education, MQ, MQ Technical Conference Leave a comment

IBM Hursley is Sending 5 speakers to MQTC v2.0.1.6

The IBM MQ Labs in Hursley, UK will be sending the following 5 speakers to MQTC v2.0.1.6: Mark Taylor, Dave Ware, Matthew Whitehead, Matt Leming and Rob Parker.

    Mark Taylor’s Sessions:

  • What’s New in IBM Messaging
  • Where is my Message?
  • MQ Integration with Directory Services
  • PCF Programming
  • Using and Analysing SMF data
    Dave Ware’s Sessions:

  • What can you achieve with MQ clusters?
  • An introduction to MQ publish/subscribe
  • Using publish/subscribe in an MQ network
  • Self-Service MQ
    Matthew Whitehead’s Sessions:

  • An Introduction to and Comparison of the Different MQ APIs
  • Running and Supporting MQ Light Applications
  • Hybrid Messaging with IBM Bluemix
  • IBM Messaging in the Cloud
    Matt Leming’s Sessions:

  • Introducing the IBM MQ Appliance
  • MQ Appliance Deep Dive (HA, DR etc.)
  • z/OS Connect
    Rob Parker’s Sessions:

  • MQ Security – An Overview & Recap MQ’s Various Security Features
  • MQ Security Deep – Dive into Advanced Security Configuration Options, including MQ AMS
  • Monitoring and Tracking MQ and Applications

For more information about MQTC, please go to:
http://www.mqtechconference.com

Regards,
Roger Lacroix
Capitalware Inc.

Capitalware, Education, MQ, MQ Technical Conference Leave a comment

Barry Lamkin will be Speaking at MQTC

Barry Lamkin will be presenting the following sessions at MQ Technical Conference v2.0.1.6 (MQTC):

    Barry Lamkin’s Technical Session:

  • The top ten issues in IBM MQ and IIB
    Barry Lamkin’s Vendor Sessions:

  • What is new in OMEGAMON XE for Messaging v7.3
  • What happened to my Transaction

For more information about MQTC, please go to:
http://www.mqtechconference.com

Regards,
Roger Lacroix
Capitalware Inc.

Capitalware, Education, MQ, MQ Technical Conference Leave a comment

Suganya Rane will be Speaking at MQTC v2.0.1.6

Suganya Rane of Sabre will be speaking at MQ Technical Conference v2.0.1.6 (MQTC).

    Suganya Rane’s Sessions:

  • Insourcing MQ
  • IBM MQ vs. Open Source MQ

For more information about MQTC, please go to:
http://www.mqtechconference.com

Regards,
Roger Lacroix
Capitalware Inc.

Capitalware, Education, MQ, MQ Technical Conference, Open Source Leave a comment