Tibco JMS Queue Requestor" or "JMS Queue Sender" Dinamic JMS properties mapping - tibco

I am working with Tibco BW5.I have JMS selectors string that looks like this:
SelectorString = "Name='Value' AND Name='Value' AND Name='Value' AND ...."
I need to use this string in "JMS Queue Requestor" or "JMS Queue Sender" as JMS selectors.
Solution:
For setting selectors to "JMS Queue Requestor" or "JMS Queue Sender" I am using "DynamicProperties" in "Input" tab:
For mapping SelectorString to "DynamicProperties" I created "Repeat-Until-True" group with MapData inside.
Repeat condition:
($i >= count(tib:tokenize($Start/root/SelectorString, "AND")))
I map "name" to:
tib:trim(tib:tokenize(tib:tokenize($Start/root/SelectorString, "AND")[$i], "=")[1])
I map "value" to:
substring-before(substring-after(tib:tokenize(tib:tokenize($Start/root/SelectorString, "AND")[$i], "=")[2], "'"), "'")
Then I set accumulated output to "JMS Queue Requestor" dynamic properties.
Please see screenshot:
Is there more elegant way to do this ?

Looks like you have not much experience with set-based math ... a typical "sequential programmer's approach to sets":-(
Assuming that the you have a non-hierarchical statement (containing ONLY "AND" between name value pairs) you can once translate " AND " into a single "special char" (like "¶"), use a for-each XML element with the tokenized string it by this char and then split and trim the name and values inside the for-each.
Process with mapping
ActivityInput:
That's the set-based approach which btw is much faster than the iteration loop (4 simple lines of XPath code)

Related

Fetch value from XML using dynamic tag in ESQL

I have an xml
<family>
<child_one>ROY</child_one>
<child_two>VIC</child_two>
</family>
I want to fetch the value from the XML based on the dynamic tag in ESQL. I have tried like this
SET dynamicTag = 'child_'||num;
SET value = InputRoot.XMLNSC.parent.(XML.Element)dynamicTag;
Here num is the value received from the input it can be one or two. The result should be value = ROY if num is one and value is VIC if num is two.
The chapter ESQL field reference overview describes this use case:
Because the names of the fields appear in the ESQL program, they must be known when the program is written. This limitation can be avoided by using the alternative syntax that uses braces ( { ... } ).
So can change your code like this:
SET value = InputRoot.XMLNSC.parent.(XMLNSC.Element){dynamicTag};
Notice the change of the element type as well, see comment of #kimbert.

How to get value from a column referenced by a number, from JDBC Response object of Jmeter?

I know they advice to get a cell value this way:
columnValue = vars.getObject("resultObject").get(0).get("Column Name");
as stated on jMeter doc : component reference : JDBC_Request.
But: How to access the same RS cell value by just a number of the column?
RS.get(0).get(4);
...instead of giving it a String of column Name/Label.
edit 1: Lets use Groovy/Java, instead of BeanShell. Thanks.
edit 2: The original motivation was the difference between column Name / Label, as these seem to be not fully guaranteed (? seems to be not clear here, not to me), especially due case-sensitivity ("id"/"ID", "name"/"Name"/"NAME" ..)
It should be something like:
String value = (new ArrayList<String>(vars.getObject("resultObject").get(0).values())).get(4)
More information: Debugging JDBC Sampler Results in JMeter
Be aware that according to HashMap documentation:
This class makes no guarantees as to the order of the map; in particular, it does not guarantee that the order will remain constant over time.
So the order of columns might be a big question mark.
The row itself is a HashMap, defined in source code as:
HashMap<String, Object> row
So using BeanShell syntax, you could get it as
row = vars.getObject("resultObject").get(0); // returns HashMap
In HashMap, you cannot access item (column) by ID. You could, however, apply one of the methods described here, but HashMap doesn't guarantee order, so you cannot be sure what "column 4" will contain.
If you want to be able to loop through all columns, it's better to do it in a Map style, not by index. For example using entrySet() with BeanShell:
for(Map.Entry entry : row.entrySet())
{
log.info(entry.getKey() + "=" + entry.getValue());
}
See various ways to iterate through Map here.

how to send arguments on messages.properties when JSR 303 validation

I have a class something like
class Sample{
#Min(1) #Max(20) private int num_seats;
...
}
and messages.properties like
Min.sample.num_seats = the number must be bigger than 1
Question is
how can I set the message dynamically by sending arguments as like "the number must bigger than {MIN_VALUE}"?
how can I share the message? such like "Min.* = the number .... " is possible?
Thank you Ralph it has helped me a lot to find a solution.
I would just add this:
I would use #Range in this case (except if you want two different message for min and max).
In Sample class
#Range(min = 1, max = 20)
private int num_seats;
And in messages.properties file
Range.sample.num_seats=The number must be between {2} and {1}.
Note that the min is argument numbered {2} and max is numbered {1} !
According to SPR-6730 (Juergen Hoellers comment) it should work in this way:
#Min(value="1", message="the number must be higher than {1}")
I have not tested it, but this is the way, I have understand the issue comment.
second question: You can share the text, be putting them in a message properties file.
If you use the same key as the default does, then you override the default message. If you want not to override the default message, then you need an other key, and need to write the key in currly brackets in the message attribute.
message properties file
javax.validation.constraints.Min.message=My mew default message
someOtherKey=Some Other Message
Using the other key:
#Min(value="1", message="{someOtherKey}")

Weblogic JMS consumer - using XPath in selector with quotes

I'm trying to subscribe to WebLogic JMS messages using selector containing XPath. In WebLogic, it's achieved using 'JMS_BEA_SELECT' function. Something like this:
session.createConsumer(topic, "JMS_BEA_SELECT('xpath', '/Parent/text()') = '123'");
This seem to work, but what if I need to use quotes in the expression? For example, how do I subscribe when my XPath expression is something like this (which is the only way to have namespace-insensitive query):
"//*[local-name()='Parent']/text()";
How do I specify single quotes of the above expression when I call createConsumer(topic, "WHAT GOES HERE?")?
Note that all the following variants didn't work (throw invalid expression exceptions):
"JMS_BEA_SELECT('xpath', '//*[local-name()=\\\"Parent\\\"]/text()') = '123'"
"JMS_BEA_SELECT('xpath', '//*[local-name()=\\\'Parent\\\']/text()') = '123'"
"JMS_BEA_SELECT('xpath', '//*[local-name()=\"Parent\"]/text()') = '123'"
"JMS_BEA_SELECT('xpath', '//*[local-name()=\'Parent\']/text()') = '123'"
EDIT:
Following the suggestion by #better_use_mkstemp, I tried using " and &apos; encoding. It doesn't throw exceptions, but it also doesn't select the message.
To be clear on the problem I'm having, below is the actual message I have in the queue:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<ServiceResponseNotification xmlns="http://www.mywebsite.com/services/types">
<ServiceResponse>
<IsFailure>true</IsFailure>
</ServiceResponse>
<ServiceRequestId>2642697</ServiceRequestId>
</ServiceResponseNotification>
And here's the code fragment:
Hashtable ht = new Hashtable();
ht.put(Context.INITIAL_CONTEXT_FACTORY, "weblogic.jndi.WLInitialContextFactory");
ht.put(Context.PROVIDER_URL, "...");
Context jndiContext = new InitialContext(ht);
ConnectionFactory connectionFactory = (ConnectionFactory)jndiContext.lookup("jms/TestConnectionFactory");
Destination dest = (Destination) jndiContext.lookup("jms/TestJMSQueue");
Connection connection = connectionFactory.createConnection();
Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
String sel = "JMS_BEA_SELECT('xpath', '//*[local-name()=&apos;ServiceResponseNotification&apos;]/*[local-name()=&apos;ServiceRequestId&apos;]/text()') = '2642697'";
MessageConsumer consumer = session.createConsumer(dest, sel);
Message m = consumer.receive(1);
if (m != null) {
System.out.println(((TextMessage)m).getText());
} else {
System.out.println("No messages");
}
The above code returns null, no matter if I'm encoding quotes as " or as &apos;. The XPath above, when applied over this XML using regular XPath testing code - works fine.
Another option I thought of - is to use double single-quotes, which, for example, are suggested when using ApacheMQ (I didn't try it, but this doc says it's OK: http://activemq.apache.org/selectors.html). Both below variants don't throw exceptions, but also don't select the message:
"JMS_BEA_SELECT('xpath', '//*[local-name()=''Parent'']/text()') = '123'"
"JMS_BEA_SELECT('xpath', '//*[local-name()=''Parent'']/text()') = '123'"
Any help will be greatly appreciated.
Thank you.
A few things to note:
First your syntax for the variants you tried doesn't match your example that works... is it = or ==? Is it '123'") or '123')" ?
Second there is a fair amount of info out there about this, from the w3 xpath docs:
"To avoid a quotation mark in an expression being interpreted by the XML
processor as terminating the attribute value the quotation mark can be
entered as a character reference (" or &apos;)"
Reference:
http://www.w3.org/TR/xpath/
http://bytes.com/topic/net/answers/178536-how-do-i-escape-single-tick-marks-xpath-queries
http://userscripts.org/topics/127322
http://kushalm.com/the-perils-of-xpath-expressions-specifically-escaping-quotes

How to use "Result Variable Name" in JDBC Request object of Jmeter

In JMeter I added the configuration for oracle server. Then I added a JDBC request object and put the ResultSet variable name to status.
The test executes fine and result is displayed in treeview listener.
I want to use the variable status and compare it with string but jmeter is throwing error about casting arraylist to string.
How to retrieve this variable and compare with string in While Controller?
Just used some time to figure this out and think the accepted answer is slightly incorrect as the JDBC request sampler has two types of result variables.
The ones you specify in the Variable names box map to individual columns returned by your query and these you can access by saying columnVariable_{index}.
The one you specify in the Result variable name contains the entire result set and in practice this is a list of maps to values. The above syntax will obviously not work in this case.
The ResultSet variable returned with JDBC request in JMeter are in the for of array. So if you want to use variable status, you will have to use it with index. If you want to use the first(or only) record user status_1. So you need to use it like status_{index}.
String host = vars.getObject("status").get(0).get("option_value");
print(host);
log.info("----- " + host);
Form complete infromation read the "yellow box" in this link:
http://jmeter.apache.org/usermanual/component_reference.html#JDBC_Request
Other util example:
http://jmeter.apache.org/usermanual/build-db-test-plan.html
You can use Beanshell/Groovy (same code works) in JSR233 PostProcessor to work with “Result Variable Name” from JDBC Request like this:
ArrayList results = vars.getObject("status");
for (HashMap row: results){
Iterator it = row.entrySet().iterator();
while (it.hasNext()){
Map.Entry pair = (Map.Entry)it.next();
log.info(pair.getKey() + "=" + pair.getValue());
}
}
Instead of output to log replace with adding to string with delimiters of your choice.

Resources