Настройка DeliveryMode для Spring JmsListener

Я использую Spring JMS и использую аннотированный метод @JmsListener, который обрабатывает входящие сообщения, а также отвечает на них.

Проблема в том, что мне нужно установить режим доставки NON_PERSISTENT, а используемая библиотека IBM MQ по умолчанию - PERSISTENT, которую можно было изменить только при вызове (внутреннего) метода send.

В другом вопросе здесь, о stackoverflow, было упомянуто, что можно установить режим доставки JmsTemplate, но, к сожалению, шаблон не используется для аннотированного метода @JmsListener.

После отладки я обнаружил MessagingMessageListenerAdapter, у которого есть метод postProcessProducer, который я могу перезаписать, чтобы вручную изменить настройки созданного MessageProducer. К сожалению, довольно сложно расширить этот класс и позволить Spring использовать его. У меня все заработало, но я сомневаюсь, что это лучшее решение, и при его наличии режим доставки для всех моих методов @JmsListener будет установлен на NON_PERSISTENT (пока для меня это не проблема, но, возможно, в будущем):

// bean definition in my @Configuration class:

@Bean(name = JmsListenerConfigUtils.JMS_LISTENER_ANNOTATION_PROCESSOR_BEAN_NAME)
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
public JmsListenerAnnotationBeanPostProcessor jmsListenerAnnotationProcessor() {
    return new JmsListenerAnnotationBeanPostProcessor() {
        @Override
        protected MethodJmsListenerEndpoint createMethodJmsListenerEndpoint() {
            return new MethodJmsListenerEndpoint() {

                @Override
                protected MessagingMessageListenerAdapter createMessageListenerInstance() {
                    return new MessagingMessageListenerAdapter() {

                        @Override
                        protected void postProcessProducer(MessageProducer producer, Message response)
                            throws JMSException {
                            super.postProcessProducer(producer, response);

                            producer.setDeliveryMode(DeliveryMode.NON_PERSISTENT);
                        }

                    };
                }

            };
        }
    };
}

Есть ли более простой способ установить режим доставки, когда я использую @JmsListener? Я нашел много классов, где я могу установить режим доставки, но я не нашел никакого способа сделать это на одном из bean-компонентов, которые мне пришлось определить, чтобы запустить установку JMS (например, JmsListenerContainerFactory или ConnectionFactory).

Обновлено: К сожалению, мы используем Spring 4.x и не можем обновить до 5.x

Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
В компьютерном программировании биты играют важнейшую роль в представлении и манипулировании данными на двоичном уровне. Побитовые операции...
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Приходилось ли вам сталкиваться с требованиями, в которых вас могли попросить поднять тревогу или выдать ошибку, когда метод Java занимает больше...
Полный курс Java для разработчиков веб-сайтов и приложений
Полный курс Java для разработчиков веб-сайтов и приложений
Получите сертификат Java Web и Application Developer, используя наш курс.
0
0
1 031
1

Ответы 1

В Spring 5 (в настоящее время 5.0.6) теперь вы можете установить объект QosSettings в свойстве документы здесь фабрики контейнеров responseQosSettings; прокрутите немного вниз.

Finally if you need to specify some QoS values for the response such as the priority or the time to live, you can configure the JmsListenerContainerFactory accordingly:

public class QosSettings {

    private int deliveryMode;

    private int priority;

    private long timeToLive;

    ...

}

Выглядит неплохо, но, к сожалению, мы используем Spring 4.x и не можем обновиться до 5.x (я не упомянул об этом). Есть ли какое-нибудь решение, совместимое с Spring 4?

chris922 25.05.2018 22:28

Если вы можете получить доступ к очереди, используя формат URI, посмотрите этот ответ, который я предоставил в другом сообщении SO: stackoverflow.com/questions/50333116/…

JoshMc 25.05.2018 23:12

Спасибо @JoshMc, хорошая попытка, но, к сожалению, она не работает с моим вариантом использования. Мы используем CachedMessageProducer, который всегда вызывает send со значением persistence по умолчанию, которое по-прежнему равно 2 и, следовательно, не соответствует значению из URI.

chris922 01.06.2018 10:03

Другие вопросы по теме