如何处理 IBM MQ 消息头

IBM MQ 消息可以选择性地包括附加头,或者包括 MQRFH2 头(包含 JMS 属性)的备用头。WebSphere® Application Server 应用程序可以使用 com.ibm.mq.headers 类访问来自 IBM MQ 的消息中的头以及构造发送至 IBM MQ 的消息中的头。

IBM MQ 消息头

IBM MQ 消息始终包括消息描述符 (MQMD)。它们还可以包括一些包含其他消息信息的头;例如,往返 JMS 应用程序的消息通常包括 MQRFH2 头,此头包含消息属性。IBM MQ 定义了一些头(例如 MQRFH2)的格式和用法,并且还允许用户和第三方软件提供者定义自己的定制头。

通常,应用程序不必处理 IBM MQ 消息头。大多数 IBM MQ 应用程序要么根本不使用任何头,要么仅使用 MQRFH2 头,并且在您与这些应用程序通信时,服务集成和 IBM MQ 消息传递提供程序会自动处理 MQRFH2 头。但是,如果您正在与使用或者创建附加头或不同头的 IBM MQ 应用程序通信,那么 WebSphere Application Server 应用程序可以使用 com.ibm.mq.headers 类创建它所发送的消息中的头,并且处理它接收到的消息中的头。

IBM MQ 消息中,头(如果存在头)位于消息的开头,并且在消息有效内容之前。每个头都包含描述以下头或有效内容(如果没有更多头)的字段;MQMD 包含描述第一个头或有效内容(如果没有头)的字段。MQMD 和 MQRFH2 头通常不出现在 JMS 消息中。当消息传递提供程序将 IBM MQ 消息转换成 JMS 消息时,它使用 MQMD 和 MQRFH2 头中的信息来设置 JMS 头字段和属性。同样,当消息传递提供程序将 JMS 消息转换成 IBM MQ 消息时,它使用 JMS 头字段和属性来构造 MQMD 和 MQRFH2 头。

JMS 提供程序通过将 IBM MQ 消息与 JMS BytesMessage 相互转换来处理 IBM MQ 消息中的其他头;头出现在消息体开头,后跟 IBM MQ 消息有效内容(如果有)。JMS 消息的 JMS_IBM_Format 属性指示消息体(在本例中,为第一个头)中的数据格式,而 JMS_IBM_EncodingJMS_IBM_Character_Set 属性指示其编码和 CCSID。

处理 JMS BytesMessage 中的 IBM MQ 消息头

com.ibm.mq.headers 包中包含可用来解析和处理 JMS BytesMessage 正文中的 IBM MQ 头的类和接口。MQHeader 接口提供一般用途的方法,用于访问头字段和读写消息内容。每种头类型都有自己的类,用于实现 MQHeader 接口以及为各个字段添加 getter 和 setter 方法。例如,MQCIH 类表示 MQCIH(CICS® 网桥)头类型。头类会自动执行任何必需的数据转换,并且可以读写任何指定的数字编码或字符集 (CCSID) 中的数据。

两个辅助类 MQHeaderIterator 和 MQHeaderList 可帮助读取和解码(解析)消息中的头内容:
  • MQHeaderIterator 的工作方式类似于 java.util.Iterator。由于只要消息中有更多的头,next() 方法就返回 true,而 nextHeader()next() 方法返回下一个头对象。
  • MQHeaderList 的工作方式类似于 java.util.List。同 MQHeaderIterator 一样,此辅助类将解析头内容,但它还允许您搜索特定头、添加新的头、移除现有头、更新头字段,然后将头内容写回到消息中。另外,您还可以创建一个空的 MQHeaderList,然后在此辅助类中填充头实例并将其写入消息一次或者重复写入。

每个头类都实现 MQHeader 接口,此接口提供方法 int read (java.io.DataInput message, int encoding, int characterSet)int write (java.io.DataOutput message, int encoding, int characterSet)。java.io.DataInputStream 和 java.io.DataOutputStream 类分别实现 DataInput 和 DataOutput。 您可以从 JMS 消息所携带的字节数组中获取 DataInput 和 DataOutput 对象,如以下示例所示,此示例处理单一 MQCIH 头:

import java.io.*;
import javax.jms.*;
import com.ibm.mq.headers.*;
...
BytesMessage bytesMessage = (BytesMessage) msg; // Message received from JMS consumer
byte[] bytes = new byte [(int) bytesMessage.getBodyLength ()];
bytesMessage.readBytes (bytes);
DataInput in = new DataInputStream (new ByteArrayInputStream (bytes));
MQCIH cih = new MQCIH (in, 
   bytesMessage.getIntProperty("JMS_IBM_Encoding"), 
   819); 

另外,您也可以通过将以 MQCIH cih = new MQCIH 开头的行替换为以下内容,从而使用 MQHeaderIterator 类来处理头序列:

MQHeaderIterator it = new MQHeaderIterator (in, 
   bytesMessage.getStringProperty("JMS_IBM_Format"), 
   bytesMessage.getIntProperty("JMS_IBM_Encoding"), 
   819);
while (it.hasNext()) {
   MQHeader item = (MQHeader) it.next();
   ...
}

此示例创建单一头(MQCIH 类型的头)并将其添加到 BytesMessage 中:

import java.io.*;
import javax.jms.*;
import com.ibm.mq.constants.CMQC;
import com.ibm.mq.headers.*;
...
MQCIH header = new MQCIH();
ByteArrayOutputStream out = new ByteArrayOutputStream ();

header.write (new DataOutputStream (out), CMQC.MQENC_NATIVE, 819);
byte[] bytes = out.toByteArray ();
BytesMessage newMsg = origSes.createBytesMessage();
newMsg.writeBytes(bytes);

此示例使用 MQHeaderList 类将两个头添加到 BytesMessage 中:

import java.io.*;
import javax.jms.*;
import com.ibm.mq.constants.CMQC;
import com.ibm.mq.headers.*;
...
byte[] outheaders = null;
byte[] outbody = ...
try {
    MQHeaderList it = new MQHeaderList ();
    MQHeader header1 = ... // Could be any header type
    MQHeader header2 = ... // Could be any header type
    ByteArrayOutputStream out = new ByteArrayOutputStream ();
    DataOutput dout = new DataOutputStream(out);
    it.add(header1);
    it.add(header2); 
    it.write(dout);
    outheaders = out.toByteArray();
} catch (Exception e) {
    System.out.println("error generating MQ message headers : " + e);
}
BytesMessage newMsg = origSes.createBytesMessage();
newMsg.writeBytes(outheaders);
newMsg.writeBytes(bytes);

newMsg.setStringProperty("JMS_IBM_Format", "MQCICS"); 
newMsg.setIntProperty("JMS_IBM_Encoding", CMQC.MQENC_NATIVE); 
newMsg.setIntProperty("JMS_IBM_Character_Set", 819);

请始终对 encoding 和 characterSet 参数使用正确的值。当您读取头时,请指定最初写入字节内容时所使用的编码和 CCSID。写入头时,请指定要生成的编码和 CCSID。数据转换由头类自动执行。

关于 com.ibm.mq.headers 类的更多信息

com.ibm.mq.headers 包是 IBM MQ 资源适配器的组成部分,该适配器自动安装到 WebSphere Application Server 中。这个包由一组类和接口组成,这些类和接口允许 Java™ 程序员处理 IBM MQ 消息头。这些类包括本主题中提及的 MQHeaderIterator 和 MQHeaderList 类以及用于一些常用的 IBM MQ 消息头的类,包括:
  • MQCIH - CICS 网桥头
  • MQIIH - IMS™ 信息头
  • MQSAPH - SAP 头

您也可以定义表示您自己的头的类。


指示主题类型的图标 参考主题



时间戳记图标 最近一次更新时间: last_date
http://www14.software.ibm.com/webapp/wsbroker/redirect?version=cord&product=was-nd-mp&topic=rjc_mqheader_proc
文件名:rjc_mqheader_proc.html