1
votes

We have messages coming from the upstream with an expiration timestamp. These messages are to be processed and sent to the downstream with a time-to-live

For various types of messages we receive different expiration timestamp and thus the time-to-live is calculated separately for each message type in a service activator and set to the outbound message header payload as below:

MessageBuilder.fromMessage(requestMessage).
setHeader("header1",header1).
setHeader("header2",header2).
setHeader("timeToLive",timeToLive).
setHeader("header3",header3).build();

Now, we are using to publish this message as below:

<int-jms:outbound-channel-adapter id="publishMessage" channel="publishMessageChannel" header-mapper="headerMapper"
                                     pub-sub-domain="${is.topic}"
                                     destination-name="${outbound.queue}" connection-factory="outputConnectionFactory" order="1" explicit-qos-enabled="true" time-to-live="headers['timeToLive']">
    <int-jms:request-handler-advice-chain>
        <ref bean="retryAdvice" />
    </int-jms:request-handler-advice-chain>    

Above is throwing the following exception as the time-to-live is set to accept only numbers

Caused by: org.springframework.beans.TypeMismatchException: Failed to convert property value of type 'java.lang.String' to required type 'long' for property 'timeToLive'; nested exception is java.lang.NumberFormatException: For input string: "'headers['timeToLive']'

We are on SI version 4.3 so cannot use the time-to-live-expression available on later versions

Need to find a way to get the value of timeToLive from enriched header set to time-to-live in int-jms:outbound-channel-adapter

1

1 Answers

2
votes

Only the way to fix it for the mentioned version is something similar what we did in the DynamicJmsTemplate and DynamicJmsTemplateProperties.

So, you need to store a dynamic value in the ThreadLocal before sending a message to the <int-jms:outbound-channel-adapter>. Extend that DynamicJmsTemplate to get access to the mentioned ThreadLocal variable in the overridden getTimeToLive() method. And clean that ThreadLocal value.