Complex response assertion in jmeter - jmeter

I'm struggling a bit to build a proper test for this scenario: basically, I'm making a POST call to a web-service and trying to assert the following:
A 201 response is ok
A 409 response is also OK (but I extract this code to a variable and attempt a retry later)
A 400 response might be OK, but only if there is a certain string in the response body
Items 1 and 2 above I got to work fine: I handle 2 with a Response Code Extractor and an If Controller later on.
My problem is: how do I test for a given substring on the response body, but only in the event of a 400 response code?
The final assertion I want to build goes something like this:
"(if the response code is 201 or 409) or (if the response code is 400 and 'substring' found in the body) then OK"

I believe that you need to use Beanshell Assertion as it is the most flexible of all assertions provided.
Relevant Beanshell code will look as follows:
if (ResponseCode.equals("201") || ResponseCode.equals("409") || (ResponseCode.equals("400") && SampleResult.getResponseDataAsString().contains("something"))) {
Failure = false;
}
See How to Use JMeter Assertions in 3 Easy Steps guide for more details on getting confidence by using JMeter Assertions.

Related

Is there a way in JMeter to get the response message from the network tab?

I am trying to get the error message from the network tab in JMeter:
I have inserted the response assertion looking for a 200 or 201. However, when a test fails, it only tells me it is looking for one of the values, but not a message like in the response section of the network tab. For example, if it is a bad request, I see the 400, but no message like "uid cannot be empty, name cannot be empty". Is there a way to pull this information in JMeter?
With "normal" Response Assertion you cannot, if you want to apply some custom logic you need to perform some custom scripting.
For example if you want to add response body to the Assertion message you can play the following trick:
Add JSR223 Assertion after the Response Assertion
Put the following code into "Script" area:
prev.getAssertionResults().each { assertionResult ->
if (assertionResult.isFailure()) {
assertionResult.setFailureMessage(assertionResult.getFailureMessage() +
System.getProperty('line.separator') +
'Response data:' +
System.getProperty('line.separator') +
prev.getResponseDataAsString())
}
}
That's it, the above code will add the response data to any failing assertion, hopefully this is what you're looking for.
Going forward you might want to migrate all the assertion logic into the JSR223 Assertion and Groovy, see Scripting JMeter Assertions in Groovy - A Tutorial article for more details.

Extract JSON response status code from Sampler Result by using JSON extractor

I'm writing a script in Beanshell and validating it by checking first the response status that JSON response has sent i.e "200" but unable to find out the way to extract it.
Since JMeter 3.1 it is recommended to use Groovy for scripting as Groovy performance is much better than other scripting options so consider migrating to JSR223 Test Elements on next available opportunity.
You won't be able to use JSON Extractor there as this 200 status code is related to HTTP protocol. Normally JMeter automatically considers HTTP status codes below 400 as successful, however if you need to perform an explicit check I would recommend going for Response Assertion. The relevant configuration would be
If you still want to continue with checking response status code via scripting you can do it using JSR223 Assertion and the following code:
if (!SampleResult.getResponseCode().equals("200")) {
AssertionResult.setFailure(true);
AssertionResult.setFailureMessage("Response code was not 200, received: " + SampleResult.getResponseCode())
}
You need to add a Response Assertion for checking HTTP status
Field to Test Instructs JMeter which field of the Request or Response to test.
Response Code - e.g. 200

how can I run multiple if controller in jmeter

I am currently working in a heavy load test, I have one login request which access with user and password and basic auth, I have to validate some info from the response and I am using assertions but I need to apply different kind of assert depending on the code response and to be able to do that I am using an if control putting the assertions inside as a child, the problem begins when I try to execute the assertions with an error code response, some how the if controller is not taking the value of the variable I created to store the code response. could some one help me? thanks!
You cannot put assertion as a direct child of the If Controller. In fact you can, however it will not make any sense as assertions obey JMeter Scoping Rules and since there is no any Sampler in the Assertion scope - it will simply not get executed.
I would recommend going for JSR223 Assertion where you have all power of Groovy SDK and JMeter API in order to set up your custom pass/fail criteria. The pseudo code would be something like:
if (SampleResult.getResponseCode().equals('200')) {
//do what you need when response code is 200
//for example let's check if response contains "foo" line
if (!SampleResult.getResponseDataAsString().contains('foo')) {
AssertionResult.setFailure(true)
AssertionResult.setFailureMessage('Failed to find "foo" line in the response')
}
}
else if (SampleResult.getResponseCode().equals('300')) {
//do what you need when response code is 300
}
else if (SampleResult.getResponseCode().equals('400')){
//do what you need when response code is 400
}
else {
AssertionResult.setFailure(true)
AssertionResult.setFailureMessage('Unexpected response code: ' + SampleResult.getResponseCode())
}
References:
SampleResult documentation
AssertionResult documentation
Scripting JMeter Assertions in Groovy - A Tutorial

Conditionally Save responses to a file based on HTTP code or body string

I'm a newbie in using Jmeter and searching for a solution solving the following problem: I have a suite that contains a set of atomic HTTP requests and the goal is to save response bodies into an xml file. Currently, I'm handling that with using "Save Responses to a file listener", but need to be able to save separately error and OK responses in different XML, based on response HTTP code and body string.
to illustrate the case with dummy code
if (HTTP response code == 200 OK && body does not contain "ERROR") then
save response to file (%path%\responsename_OK.xml
else
save response to file (%path%\responsename_ERROR.xml
My bad, Nikolay, I forgot you wanted it in xml format...
Well, the easiest way is to add 2 Simple Data Writers (SDW) to each HTTP Request where 1 SDW logs only errors and the other logs only successes.
The Pro's are
it's easy and once you set it up for 1 HTTP Request, you can simply copy it to every other HTTP Request
Each success or failure with be appended to the corresponding .xml file
You can define as much or as little detail as you want
The Con is you add 2 elements to each Request, thus increasing your test size twice as much as you would with a BeanShell Assertion. (if that's a concern for you.)
If you want a more detailed way, you could try a BeanShell Assertion scripted with XML Parsers and XPath Assertions like outlined here.
Use Response Assertion (in fact you will need 2: one for Response Code and another one for Response Body checking) in order to fail the request basing on these criteria
Use If Controller for setting a condition:
${JMeterThread.last_sample_ok} will be triggered if previous sampler is successful
!${JMeterThread.last_sample_ok} - will fire if previous sampler fails
N.B. you should have any Sampler under the If Controller so it could work.

how to make the jmeter sampler result to pass deliberately

I've one simple jmeter login script for negative scenarios which takes invalid login and password.
It gives JSON response as
{
"status": 401,
"error": "unauthorised",
}
The above response is expected.
I've also added the JSON Path Assertion to verify the status code as 401 which validates correctly
Now my target is if I run the test it should pass however its coming as fail status.
Sampler result shows as below
Sample Count: 1
Error Count: 1
How I can make it pass? Is it possible or not?
One more way is to add a BeanShell PostProcessor to that sample with prev.setResponseOK();
This will pass the previous sample irrespective of whatever result it got.
You can try to add Response Assertion to your HTTP sampler and set check-box 'Ignore Status'. Then response will have status 403 and 'Error Count' equals to 0. Does it give result what you want?
Upd: Oops, author has already got the answer. Sorry

Resources