We have WSO2 ESB listening on to a single ActiveMQ Queue. However we want to configure multiple proxies on listening on to the JMS queue.. however we want the proxy to only consume message meant for it.
Is there a mechanism to set JMS Message selector on the ESB Proxy so that it consumes only message designated for it. ?
Thanks
Rajiv Patil
AFAIK it is not possible to perform such a selection. However there are two possible approaches to achieve the above.
Let each proxy read all the messages and select which to process inside the proxy itself
Use an EIP pattern to achieve the above. One possible pattern would be Message Routing where you can select the messages and direct the message to the desired sequence or proxy which will do the processing.
Yes, you can have multiple proxy services listening to the same queue, each following a certain JMS MessageSelector. You will have to set the transport.jms.MessageSelector parameter for each proxy like this (value 100 is variable, each proxy service containing a different number):
<parameter name="transport.jms.MessageSelector">account='100'</parameter>
And the Java message producer sending the message to the JMS broker is setting the message selector with:
// this will set a key/value pair as JMS message selector
// 100 should be a variable in your case
message.setStringProperty("account", "100");
This was tested on ActiveMQ 4.7 and WSO2 ESB 4+.
Related
I am after the wso2 configuration/source code for a wso2 ESB proxy that can read from a WebSphere MQ Queue and write to a WebSphere MQ Queue. One way, no response.
We need reliability, i.e. the message can never be lost. No matter what the failure scenario. For any failures writing to the output queue, the message should be rolled-back to the input queue (this probably means the message should be read from the input queue using a transaction and/or client acknowledgement mode).
Examples of failures are:
Output queue full, MQRC 2053
Output queue does not exist, MQRC 2085
Output queue put inhibited
Output queue max msg size smaller than the size of the message to be sent.
Application does not have authority to send to output queue, MQRC 2035
Ideally we are trying to do this using just a wso2 ESB proxy, not a wso2 message store or wso2 message processor. Please clarify if this is possible to do using only the wso2 esb proxy, and not the other components. If this is not possible, please provide full configuration using the message store and message processor.
I am able to create a wso2 proxy to read from WebSphere MQ and write to WebSphere MQ, however in any of the failure scenarios above we lose messages.
Update at 1 June 2015: wso2 support have replicated this issue and are looking into supplying a fix/solution. I am using wso2 ESB 4.8.1.
In your proxy definition, add thoses parameters :
<parameter name="transport.jms.SessionAcknowledgement">CLIENT_ACKNOWLEDGE</parameter>
<parameter name="transport.jms.SessionTransacted">true</parameter>
In it's faultSequence : add this property :
<property name="SET_ROLLBACK_ONLY" value="true" scope="axis2"/>
You must not use "send" mediator in your inSequence, because it works asynchronously and the inSequence ends before the outSequence receive the response (or before the faultSequence receive the fault) : as soon as the inSequence ends, if property "SET_ROLLBACK_ONLY" has not been set, dequeue of the message is committed !
You can use "call" mediator. Property "ClientApiNonBlocking" can be usefull in some cases. You can use "filter" mediator after "call" mediator in your inSequence to analyse the response and decide to rollback the transaction setting "SET_ROLLBACK_ONLY" property.
I have successfully configured the WSO2 Message Broker with my WSO2 ESB. I have also implemented successfully the JMS Transactions. It means that if there is an error in Service Normal Flow, Message will be rolledback.
Problem:
Previously i have configured the ActiveMq with my ESB. In that Setup i have a configuration in {ESB_HOME}/repository/conf/axis2/axis2.xml. This configuration donates the "Re-delivery Delay". This time is used to tell the MessageBroker(ActiveMQ) that when you are attempting to redeliver the message, you have to wait for this time before trying again.
<parameter name="redeliveryPolicy.redeliveryDelay" locked="true">1200000</parameter>
WSO2 Message Broker:
I want to achieve the same result in WSO2 Message Broker. I think it had to do with some configuration in {MB_HOME}/repository/conf/advanced/andes-config.xml. But i am unable to find that particular configuration setting anywhere in Message Broker.
Note: I am using WSO2 ESB 4.8.1 and WSO2 Message Broker 2.2.0.
What i want to achieve:
My goal is that i should be able to tell WSO2 Message Broker like ActiveMQ that you must take this much time before trying to re-deliver the message.
As I know it cannot be done like this in case of WSO2 MB. You have to setup a message store and a message processor guarding on that message store. And when you have a message processor it can be configured with interval and max delivery attempts.
https://docs.wso2.com/display/IntegrationPatterns/Dead+Letter+Channel
http://charith.wickramaarachchi.org/2012/05/another-message-redelivery-pattern-with.html
http://wso2.org/library/articles/2011/10/implementing-store-forward-messaging-patterns-wso2esb-part-1
http://wso2.com/library/articles/2011/12/implementing-store-forward-messaging-patterns-wso2esb-part-2/
(Alternatively, you can setup the maxAckWaitTime, it means it will wait at least 'maxAckWaitTime' seconds between two redelivery attempts)
I am a novice user for jmeter.
In my company i need to do load testing. I am using Hermes JMS to send request and response using the queues. So what should I use in jmeter, jms point to point or JMS publisher and subscriber. And I also want to set up the ftp location to get the files.
I tried both of those but getting the error in jndi properties:
"ERROR - jmeter.protocol.jms.sampler.JMSSampler: org.apache.activemq.jndi.ActiveMQInitialContextFactory javax.naming.NameNotFoundException: org.apache.activemq.jndi.ActiveMQInitialContextFactory"
I am not exactly sure how can I set up the queues that I am using in hermes.
How can I setup the JNDI settings? Or its default because I was reading online and everyone has Initial Context Factory as org.apache.activemq.jndi.ActiveMQInitialContextFactory and what about the queues do I need to provide my own queues or that's the default as well?
If you are using queues, you'll want to use JMS point to point. JMS publisher and subscriber uses JMS topics. If the queues already exist in ActiveMQ (and they appear to since you can see them in Hermes), you'll need to configure JMeter to use those. It sounds like your JNDI settings are incorrect and JMeter cannot find the JNDI name you're telling it to look for.
Regarding the 2nd part of your question: when using a JMS Publisher, you can use the dynamicQueues/ prefix for your destination when creating queues, dynamicTopics/ for topics, e.g. dynamicQueues/my.testqueue
You need to make sure that you have the 'activemq-all-[version].jar' file in the lib folder of JMeter so that when you set the 'Initial Context Factory' property to 'org.apache.activemq.jndi.ActiveMQInitialContextFactory' (as well as the 'QueueConnection Factory' resource to 'ConnectionFactory') in the JMS Sampler the latter is found and initiated by JMeter.
In weblogic it is possible to create a message bridge between two JMS message queues. While configuring this bridge, a message filter can be applied so that the bridge will route messages that match the filter only.
Is it possible to achieve the same with Websphere?
Specifically I'm trying to achieve this scenario.
I have one source queue on which messages are received. Each message will have a custom JMS property set up. I would like to forward the messages on the source queue, to separate queues based on the JMS property and its value. This is easily configured in WLS using message bridges with filtering. How can I do the same in WAS?
Thanks
Savio
You need to use SIB Mediation.
The WAS info center have an example called writing a routing mediation which seems like what you need.
At the bottom of the example there is a link to what to do next which also explains how to configure WAS to use that mediation.
Without writing custom code (as per your comment on Aviram's answer), it is not possible to achieve the exact same thing, but nonetheless it is possible to achieve same effect;
You say that a 'source queue' distributes messages to other 'separate queues' according to a custom JMS property. I'm assume that you have MDBs (message driven beans) configured to process messages in these separate queues.
What you can do with WebSphere is distribute messages to these MDBs directly from the 'source queue', without having to filter/distribute them to separate queues.
This is managed by using JMS Message Selectors. You can point all your MDBs to the source queue using activation specification definitions, and for each (one for each type of message) MDB, define a JMS Message Selector that matches the ones you use in WLS. This way each message is only delivered the MDB whose filter matches the message's properties. This effectively filters/distributes messages to different MDB's as in WLS.
You may read details on configuring message selectors (during development in RAD, or at/after deploy time) at infocenter. Below is a quote to give you an idea about what it look like;
messageSelector
This attribute determines the JMS message selector
that is used to select which messages the message-driven bean
receives. For example:
JMSType='car' AND color='blue' AND weight>2500
The selector string can refer to fields in the JMS message header and
fields in the message properties. Message selectors cannot reference
message body values.
For the record, we finally ended up writing our own routing algorithm within the application to ensure that messages are sent to separate queues for each client. This way we are independent of app server implementations and the integration effort is the same across app servers, viz., adding custom queues per integrating client.
In brief, We published a JMS custom property that must be set. Using a published convention, we look up for a queue and send responses to the queue. If the property is not set, a default queue is created to route all messages. If the property is set, and the queue cannot be found an exception is raised and processing halted.
This suited our purpose. Hope it helps...
When sending (InOnly) JMS messages with Apache Camel, can I read back the different JMS headers that might have been set automatically on the message, when it was sent?
from("foo:bar")
.to(ExchangePattern.InOnly,"jms:queue:whatever")
.log("msg id set = ${in.header.JMSMessageId}");
I just can't figure out how to send the message "one way" but keeping the sent JMS message as "in" message in the route afterwards.
Background:
I know that I can present some values, but it would be easier if they where set by the actual JMS implementation. For instance, in this case, I want to work with WebSphere SIBus, WebSphere MQ and ActiveMQ. It's best to rely on WebSphere MQs internal message id format, because it will only index certain message formats. It might be similar aspects on the WebSphere SIBus implementation.
This feature is available starting at 2.10.3 and 2.11.0.