Consider supporting spring-jms binding · Issue #141 · tracee/tracee · GitHub
Skip to content
This repository was archived by the owner on Feb 4, 2024. It is now read-only.
This repository was archived by the owner on Feb 4, 2024. It is now read-only.

Consider supporting spring-jms binding #141

Description

@Hippoom

spring-jms provides JmsTemplate to hide message sending implementations.

To send Message with current TPIC, one can override JmsTemplate's

 protected MessageProducer createProducer(Session session, Destination destination) throws JMSException {
} 

method to return a TraceeMessageProducer. But it's not opaque to the client. Another approach is wrap ConnectionFactory and inject it to JmsTemplate:

@Bean
protected ConnectionFactory connectionFactory() {
    ActiveMQConnectionFactory activeMQConnectionFactory = new ActiveMQConnectionFactory("vm://localhost?broker.persistent=false");
    TraceeWrappedConnectionFactory traceeWrappedConnectionFactory = new TraceeWrappedConnectionFactory();
    traceeWrappedConnectionFactory.setTargetConnectionFactory(activeMQConnectionFactory);
    return traceeWrappedConnectionFactory;
}

@Bean
protected JmsTemplate jmsTemplate() {
    JmsTemplate template = new JmsTemplate(connectionFactory());
    return template;
}

The TraceeWrappedConnectionFactory is actually a DelegatingConnectionFactory which will return a TraceeWrappedConnection for createSession() invocation. TraceeWrappedConnection also follows Delegation Pattern and returns a Delegating TraceeWrappedSession which will return TraceeMessageProducer in the end.

On the receiving side, the only way I find without AOP is provide a subclass of DefaultMessageListenerContainer and overrides invokeListener() or doExecuteListener() like this:

protected void invokeListener(Session session, Message message) throws JMSException {
    beforeProcessing(message);
    try {
        super.invokeListener(session, message);
    } finally {
        cleanUp();
    }
}

For spring-jms 2.x, one can setup the context using:

<bean id="jmsContainer" class="spike.TraceeMessageListenerContainer">
    <property name="connectionFactory" ref="connectionFactory"/> 
    <property name="destination" ref="hi"/>
    <property name="messageListener" ref="messageListener"/>
</bean>

For spring-jms 4.x, one more component is needed, TraceeJmsListenerContainerFactory overrides createContainerInstance(), returns TraceeMessageListenerContainer instead of default DefaultMessageListenerContainer:

@Bean
public DefaultJmsListenerContainerFactory myJmsListenerContainerFactory() {
    DefaultJmsListenerContainerFactory factory = new TraceeJmsListenerContainerFactory();
    factory.setConnectionFactory(connectionFactory());
    return factory;
}

As long as one provided a TraceeWrappedConnectionFactory, the request-reply case is also covered.

Metadata

Metadata

Assignees

Type

No type

Fields

No fields configured for issues without a type.

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions