【问题标题】:Spring JMS + IBM MQ: How to set message buffer size or wait timeout?Spring JMS + IBM MQ:如何设置消息缓冲区大小或等待超时?
【发布时间】:2016-03-26 10:27:31
【问题描述】:

我无法处理来自 IBM MQ 的大消息并收到以下错误:

JMSCMQ0001:WebSphere MQ 调用失败,compcode '1' ('MQCC_WARNING') 原因 '2080' ('MQRC_TRUNCATED_MSG_FAILED')

我正在使用 DefaultListenerContainer,而不是直接使用 IBM MQ Java API 类通过 MessageConsumer 进行消费。我相信通过使用 IBM MQ JMS API,您可以在从队列中检索消息之前使用特定选项。但是我如何使用 DefaultListenerContainer 来做到这一点,我可以为这些设置系统属性吗?

如果使用 IBM MQ JMS API(我不使用这样的消息,粘贴仅供参考):

MQGetMessageOptions mqGetMessageOptions = new MQGetMessageOptions(); mqGetMessageOptions.waitInterval = ipreoProperties.getMqReceiveWaitTime(); mqGetMessageOptions.options = MQC.MQGMO_WAIT | MQC.MQPMO_SYNCPOINT | MQC.MQGMO_ACCEPT_TRUNCATED_MSG;

以下是我用于 IBM MQ 连接的 Java 配置:

@Bean
    public CachingConnectionFactory ipreoMQCachingConnectionFactory() {

        CachingConnectionFactory cachingConnectionFactory = new CachingConnectionFactory();

        //Not defining MQQueueConnectionFactory as separate bean as Spring boot's auto-configuration finds two instances
        //of ConnectionFactory and throws ambiguous implementation exception 
        //One implementation is CachingConnectionFactory and other one would be MQQueueConnectionFactory if defined separately

        MQQueueConnectionFactory mqConnectionFactory = new MQQueueConnectionFactory();

        try {

            mqConnectionFactory.setHostName(env.getRequiredProperty(AppEnvPropertyConstants.JmsConstants.IPREO_MQ_HOSTNAME));
            mqConnectionFactory.setQueueManager(env.getRequiredProperty(AppEnvPropertyConstants.JmsConstants.IPREO_MQ_QUEUE_MGR));
            mqConnectionFactory.setPort(env.getRequiredProperty(AppEnvPropertyConstants.JmsConstants.IPREO_MQ_PORT, Integer.class));
            mqConnectionFactory.setChannel(env.getRequiredProperty(AppEnvPropertyConstants.JmsConstants.IPREO_MQ_CHANNEL));
            //mqConnectionFactory.setTransportType(WMQConstants.WMQ_CM_CLIENT);

            //Setting connection mode as Client so it doesn't complain for native IBM MQ libraries
            mqConnectionFactory.setIntProperty(CommonConstants.WMQ_CONNECTION_MODE, CommonConstants.WMQ_CM_CLIENT);

        } catch (JMSException exception) {
            exception.printStackTrace();
        }

        cachingConnectionFactory.setTargetConnectionFactory(mqConnectionFactory);

        //Setting session caching size as 10, don't think we need more
        cachingConnectionFactory.setSessionCacheSize(10);
        cachingConnectionFactory.setReconnectOnException(true);

        return cachingConnectionFactory;
    }

 public DefaultMessageListenerContainer ipreoDealActivityListenerContainer() {

        DefaultMessageListenerContainer factory = new DefaultMessageListenerContainer();
        factory.setConnectionFactory(ipreoMQCachingConnectionFactory());
        factory.setDestinationName(env.getRequiredProperty(AppEnvPropertyConstants.JmsConstants.IPREO_DEAL_QUEUE_NAME));
        factory.setMessageListener(ipreoDealActivityListener());
        factory.setSessionAcknowledgeMode(Session.AUTO_ACKNOWLEDGE);

        return factory;
    }

@Bean
    public MessageListener ipreoDealActivityListener() {
        return new IpreoDealActivityListener();
    }

感谢您的帮助,谢谢。

【问题讨论】:

    标签: spring-boot ibm-mq spring-jms


    【解决方案1】:

    添加延迟响应,因为它可能对某人有用。

    在我的例子中,当 java 客户端出现这个异常时,我们注意到实际消息大小大于默认的 4 MB 缓冲区大小。

    Java API 不提供更改缓冲区大小的挂钩。因此,缓冲区大小必须在 MQ 服务器级别更新。

    首先,我们增加了队列属性中的消息大小 - 它不起作用。

    然后,我们在 MQ 通道级别也增加了消息大小属性,最终解决了这个问题。

    总而言之,增加队列和通道的 MQ 服务器的缓冲区大小。

    【讨论】:

      【解决方案2】:

      在客户端连接到队列管理器时,您可以限制服务器端和客户端的消息大小。在客户端限制小于消息大小之前,我已经看到此错误。

      我不知道如何直接在 JMS 客户端中设置消息大小限制,但您可以使用客户端通道定义表。它是一个包含连接到队列管理器的详细信息的文件,在队列管理器上创建,然后复制到客户端主机。您需要通过在连接工厂上发出 setCCDTURL 来引用该文件(使用 CCDT 时不需要设置主机、端口和通道,CCDT 会指定这些)。

      在队列管理器上创建 CCDT 时,需要在客户端通道上设置适当的消息大小限制。

      在服务器连接通道上设置服务器端限制。

      【讨论】:

        【解决方案3】:

        在我们自动处理的接收缓冲区的 JMS 客户端代码处理中;理论上,JMS 应用程序永远不会收到特定错误。

        第一个 sn-p 代码是 Java 类 API,这可能会出现该错误。

        这些消息实际上有多大?您使用的是什么级别的 JMS 客户端代码 - 确保它是最新版本。当然是 7.5 或 8 版本之一。

        这个answer 也有更多关于此的信息。

        【讨论】:

          猜你喜欢
          • 2017-12-26
          • 1970-01-01
          • 1970-01-01
          • 2010-11-14
          • 2011-01-20
          • 2020-09-29
          • 1970-01-01
          • 1970-01-01
          • 2021-01-23
          相关资源
          最近更新 更多