Spring JMS 和本机 IBM MQ 库之间总消息长度的差异

问题描述

我向 MQ 队列 (MQ 7.0.1) 发送了一条简单的文本消息: "abc"

  • 使用 spring JMS,消息的总长度为:291

    spring jms total length

spring jms properties with names

  • 但是使用 IBM MQ 库将相同的消息放入队列中,消息的总长度为:3

    ibm mq libraries total length

如何使用 JMS 获得总数据长度为 3?

Spring JMS 代码

@EnableJms
public class JMSTestController {
...

@Autowired
private jmstemplate jmstemplate;

@Autowired
JmsMessagingTemplate jmsMessagingTemplate;

...

public String send() throws JMSException{
    jmstemplate.setReceiveTimeout(10000);
    jmsMessagingTemplate.setjmstemplate(jmstemplate);
    
    Session session = jmsMessagingTemplate.getConnectionFactory().createConnection()
            .createSession(false,Session.AUTO_ACKNowLEDGE);
    
    Queue entryQueue = session.createQueue("hereQueueName");
    Queue replyQueue = session.createQueue("hereReplyQueueName");


    TextMessage message = session.createTextMessage("abc");
    message.setJMSDeliveryMode(DeliveryMode.NON_PERSISTENT);
    message.setJMSDestination(entryQueue);
    message.setIntProperty(WMQConstants.JMS_IBM_CHaraCTER_SET,819);
    message.setIntProperty(WMQConstants.JMS_IBM_ENCODING,273);

    jmsMessagingTemplate.convertAndSend(entryQueue,message);

    String messageId = message.getJMSMessageID();
    ...    

}

本机代码

MQQueueManager qm = createQueueManager(queueManager,host,port,channel,username,password,connectionType);
MQQueue m_receiver = null;

MQMessage msg = new MQMessage();
msg.format = MQC.MQFMT_STRING;
msg.expiry = timeout / 1000;
msg.replyToQueueName = qReceiver;
msg.replyToQueueManagerName = queueManager;
msg.write("abc".getBytes());
MQPutMessageOptions pmo = new MQPutMessageOptions();
try {
    qm.put(qSender,msg,pmo);
} catch (MQException e) {
    MQTalkerException ex = new MQTalkerException(
            "An error happened sending a message",e);
    logger.error(ex);
    throw ex;
}

解决方

根据 JoshMc 的评论,我做了以下修改,达到了预期的效果

看看这些答案,你想把targetClient设置成MQ来去掉 那些属性。有很多方法可以做到这一点,改变 您的 CreateQueue 使用 URI 可能是最简单的。 JMS transport v/s MQ transport

也就是说,使用 URI 而不是仅使用其名称修改队列的创建。

Queue entryQueue = session.createQueue("queue:///QUEUE_NAME?targetClient=1");

解决方法

我按照 JoshMc 的评论找到了解决方案。也就是说,使用 URI 而不是仅使用其名称来修改队列的创建。

Queue entryQueue = session.createQueue("queue:///QUEUE_NAME?targetClient=1");

这将删除 MQRFH2 标头(我不知道它们来自哪里的额外字节) 并且该消息的总长度为 3 个字节。

,

Spring 正在计算消息的字节数 body(又名 data

IBM MQ 本机正在计算消息的字节数headers 加上 body

在您的屏幕截图中,正上方的字段显示“3”字节。

纵向数据 = 正文长度 = 3

纵向总计 = 标题长度 + 正文 = 291