Jmeter Backend Listener groovy issues - regex

I'm trying to add a JMeter backend listener to my JMeter project so I can have all the metrics in real-time in Graphite. My tests run distributed on several nodes and I want to know the hostname in as part of the graphite path. I tried to incorporate JSR223 scripts, but those are not evaluated before the listeners start, so I used the __groovy() method for the rootMetricsPrefix field, like this:
${__groovy(vars.get(vars.get("environment")+".graphiteprefix"))}.server.
${__groovy(InetAddress.getLocalHost().getHostName()
.replaceAll(/^([^.]*).*$/){m,host->return host})}.
myappbucket.jmeter.
The first part gets the variable with the name "environment" to get the root prefix for the environment ("test", "load", etc). The seconds __groovy() script should get the first part of the hostname. It works if I add it as a JSR223 sampler (to test it), but if I try to use it as a variable, I get the following error:
Script13.groovy: 1: expecting '}', found '' # line 1, column 67.
me().replaceAll(/^(^\.).*$/){m
^
1 error
at org.codehaus.groovy.jsr223.GroovyScriptEngineImpl.eval(GroovyScriptEngineImpl.java:158) ~[groovy-all-2.4.13.jar:2.4.13]
at javax.script.AbstractScriptEngine.eval(AbstractScriptEngine.java:233) ~[?:1.8.0_152]
at org.apache.jmeter.functions.Groovy.execute(Groovy.java:121) [ApacheJMeter_functions.jar:4.0 r1823414]
at org.apache.jmeter.engine.util.CompoundVariable.execute(CompoundVariable.java:137) [ApacheJMeter_core.jar:4.0 r1823414]

According to JMeter documentation:
If a function parameter contains a comma, then be sure to escape this with "\", otherwise JMeter will treat it as a parameter delimiter. For example:
${__time(EEE\, d MMM yyyy)}
So you need to escape the comma between m and host
${__groovy(InetAddress.getLocalHost().getHostName() .replaceAll(/^(^\.).*$/){m\,host->return host})}. myappbucket.jmeter.
Also be aware of __machineName() and __machineIP() functions, they provide a little bit easier way of getting the hostname and IP address of the JMeter Engine. See Apache JMeter Functions - An Introduction article for more comprehensive information on JMeter Functions

Related

Regex to differentiate APIs

I need to create a regex to help determine the number the number of times an API is called. We have multiple APIs and this API is of the following format:
/foo/bar/{barId}/id/{id}
The above endpoint also supports query parameters so the following requests would be valid:
/foo/bar/{barId}/id/{id}?start=0&limit=10
The following requests are also valid:
/foo/bar/{barId}/id/{id}/
/foo/bar/{barId}/id/{id}
We also have the following endpoints:
/foo/bar/{barId}/id/type/
/foo/bar/{barId}/id/name/
/foo/bar/{barId}/id/{id}/price
My current regex to extract calls made only to /foo/bar/{barId}/id/{id} looks something like this:
\/foo\/bar\/(.+)\/id\/(?!type|name)(.+)
But the above regex also includes calls made to /foo/bar/{barId}/id/{id}/price endpoint.
I can check if the string after {id}/ isn't price and exclude calls made to price but it isn't a long term solution since if we add another endpoint we may need to update the regex.
Is there a way to filter calls made only to:
/foo/bar/{barId}/id/{id}
/foo/bar/{barId}/id/{id}/
/foo/bar/{barId}/id/{id}?start=0&limit=10
Such that /foo/bar/{barId}/id/{id}/price isn't also pulled in?
\/foo\/bar\/(.+)\/id\/(?!type|name)(.+)
There is something in your RegEx which is the cause to your problem. "(.+)" RegEx code matches every character after it. So replace it with "[^/]" and add the following code "/?(?!.+)". This is working for me.
/foo/bar/([^/]+)/id/(?!type|name)([^/]+)/?(?!.+)

JMeter '&' Character not Encoded as '&' in the URL

When request extracts a URL variable from XML document through XPath Extractor and Regular Expression Extractor it decodes the encoded characters in the extracted URL.
For example, the URL in the XML file:
<url>www.testing.com/test/request?parameter1=test1&parameter2=test2</url>
The & between the two URL parameters become & which affect my testing final results.
Is there any way to prevent special characters decoding in JMeter?
Normally JMeter should not perform encoding and decoding of variables during extraction, the variable should be sent as is so most probably something is wrong with your test logic. You can double check the variable value using Debug Sampler and View Results Tree listener combination. See How to Debug your Apache JMeter Script article for more information on JMeter tests troubleshooting.
As a workaround you can explicitly tell JMeter to encode the variable using __escapeHtml() function like:
${__escapeHtml(${your_variable_here})}

How can I replace text in a Siebel data mapping?

I have an outgoing web service to send data from Siebel 7.8 to an external system. In order for the integration to work, before I send the data, I must change one of the field values, replacing every occurence of "old" with "new". How can I do this with EAI data mappings?
In an ideal world I would just use an integration source expression like Replace([Description], "old", "new"). However Siebel is far from ideal, and doesn't have a replace function (or if it does, it's not documented). I can use all the Siebel query language functions which don't need an execution context. I can also use the functions available for calculated fields (sane people could expect both lists to be the same, but Siebel documentation is also far from ideal).
My first attempt was to use the InvokeServiceMethod function and replace the text myself in eScript. So, this is my field map source expression:
InvokeServiceMethod('MyBS', 'MyReplace', 'In="' + [Description] + '"', 'Out')
After some configuration steps it works fine... except if my description field contains the " character: Error parsing expression 'In="This is a "test" with quotes"' for field '3' (SBL-DAT-00481)
I know why this happens. My double quotes are breaking the expression and I have to escape them by doubling the character, as in This is a ""test"" with quotes. However, how can I replace each " with "" in order to call my business service... if I don't have a replace function? :)
Oracle's support web has only one result for the SBL-DAT-00481 error, which as a workaround, suggests to place the whole parameter inside double quotes (which I already had). There's a linked document in which they acknowledge that the workaround is valid for a few characters such as commas or single quotes, but due to a bug in Siebel 7.7-7.8 (not present in 8.0+), it doesn't work with double quotes. They suggest to pass instead the row id as argument to the business service, and then retrieve the data directly from the BC.
Before I do that and end up with a performance-affecting workaround (pass only the ID) for the workaround (use double quotes) for the workaround (use InvokeServiceMethod) for not having a replace function... Am I going crazy here? Isn't there a simple way to do a simple text replacement in a Siebel data mapping?
first thing (quite possibly - far from optimal one) which is coming to my mind - is to create at source BC calculated field, aka (NEW_VALUE), which becomes "NEW" for every record, where origin field has a value "OLD". and simply use this field in integration map.

Getting Number of Occurrences of String in JMeter

I am analyzing a website that returns text (JSON array), which I'm using HTTP Request element for. What I'm trying to do is check the number of times a string appears in the response, for example a field called "itemname". So I have added a Regular Expression Extractor, put ItemNameVar as the Reference Name, ^itemname$ as the Regular Expression, $1$ for the Template, -1 for Match No, and "NOT FOUND" for Default Value. I've also added an If Controller, which says "${ItemNameVar_matchNr}" == "1", because I expect it to occur only one time. However, it never fails if I set it to a different number. What am I doing wrong here? Thank you.
It looks like to be an issue with your regular expression.
I would suggest using Beanshell Post Processor instead of Regular Expression Extractor as JSON structures aren't very handy to parse with regexes.
Reference Beanshell code will look as follows:
import org.apache.commons.lang3.StringUtils;
int matches = StringUtils.countMatches(new String(data), "itemname");
vars.put("ItemNameVar_matchNr", String.valueOf(matches));
Explanation:
First line - import necessary helper class
Second line - data is a short-hand for byte-array representation of Sampler response. Method countMatches counts number of occurrences of itemname criteria in string representation of response data. Result is saved as matches integer variable
Third line - value of matches is saved as JMeter Variable called ItemNameVar_matchNr
See How to use BeanShell: JMeter's favorite built-in component guide for more detailed explanation of Beanshell scripting in JMeter and small Beanshell cookbook containing JMeter API usage examples.
The approach you are following is absolutely correct.
Please check your Jmeter script. Make sure the next request you are trying to execute after
IF Controller is branch or within Controller
Jmeter IF Controller
Hope this will help.

How can I use details from a JSON response from JMeter in a JSR223 PreProcessor?

I'm using JMeter 2.7 to load test a web application. I have a HTTP Request Sampler that returns a JSON document that has two values I want to extract from it. To do that, I have two RegEx PostProcessors assigned to the Sampler with the following configuration:
Regular Expression Extractor
Apply to: Main Sample Only
Response Field to Check: Body
Reference Name: val_1
Regular Expression: "val_1": "(\S+)"
Template: $1$
Match No.: 1
The configuration for the second is the same, just substituting val_2 for val_1. These seem like they should work.
Now, I also have a JSR223 PreProcessor script on a subsequent HTTP request that I want to use to transform the values I'm grabbing with the regex. However, the output of vars.get('val_1') and vars.get('val_2') are both null values. Tinkering with user-defined variables and "Apply to" settings haven't yielded any useful results.
Can anyone explain what I'm doing incorrectly? How can I use data retrieved through a RegEx extractor in my JSR223 script? Thanks in advance.
Edit - 9/26/2012
It was requested that I explain the structure a bit more, so here's an outline.
Thread Group
Once Only Controller
HTTP Sampler
Regular Expression Extractor (for val_1)
Regular Expression Extractor (for val_2)
Some Additional Simple Controllers with HTTP Samplers Here
Throughput Controller (80%)
HTTP Sampler
JSR223 PreProcessor (This is the PreProcessor in question)
Regular Expression Extractor (to grab an unrelated value from the response)
Some Additional Controllers with HTTP Samplers Here
Hopefully this is more helpful.
Is your regexp "val_1": "(\S+)"?
can you add a debug sampler just after Http sampler to check that the 2 vars are defined.
To do that add a tree result listener and see what debug sampler shows.