Jmeter - get nested Json string - json

I'm using Jmeter for API test. in one of the responses I get Json that includes the same key ("id") twice - nested and not.
this is an example of the response (part of it):
{
"id": "3600f05a-2ef6-490d-95af-7742f652cbfd",
"progress": 1,
"status": "done",
"task_update_time": "2016-01-24T08:23:12.274Z",
"result": {
"id": "c8b1ed07-0b57-4473-a4d7-08f7b829aad7",
"name": "testPrintFlow",
"geom": {
now, I want to get the second (nested) "id". until now I used Regular expression extractor. I can use it also in this case, like this:
"result":{"id":"(.+?)"
but I want something more robust. I guess I can use some Json library, but I made few tries and there seem to be many holes. can someone please recommend (and explain) what is the best way? either regular expression or Json. Thanks.

Related

Correlating JSON Response Body in JMeter

I tried to design a test script of API Load Testing in JMeter 5.0. Here is my thread group info:
Below is the Body Data, I already added some variables and functions to it. You can also view the sample JSON Body Data at here:
{
"app_name": "Telekom",
"source": "MOENGAGE",
"moe_request_id": "req_${__threadNum}",
"events": [
{
"event_name": "Email Opened",
"event_code": "MOE_EMAIL_OPEN",
"event_uuid": "${__UUID}",
"event_time": ${__jexl3(${__time(,)}/1000,)},
"event_type": "CAMPAIGN_EVENT",
"event_source": "MOENGAGE",
"uid": "${__counter(,)}-${__RandomString(7,ABCDEFG123456)}${uid}",
"email_id": "${email}",
"event_attributes": {
"campaign_id": "${__RandomString(24,abcdefghijklmn123456789)}",
"campaign_name": "July2021_16072021_LigaSuper_English",
"campaign_type": "GENERAL",
"campaign_channel": "EMAIL",
"moe_delivery_type": "One Time",
"moe_campaign_tags": [
"engagement"
],
"moe_campaign_channel": "Email",
"u_em": "${email}"
},
"user_attributes": {
"PRODUCT_TYPE": "Unifi",
"moengage_user_id": "60dc48d4d722040a2e78b788",
"SERVICE_NO": "${uid}",
"id": "${email}"
},
"device_attributes": {}
}
]
}
I also include JSON Extractor to do correlation on the response body:
Here is the results in View Results Tree. Added Debug Sampler to see the whether my parameterization and correlation working or not. Fortunately, only my parameterization is working, while correlation is not.
Updated: This is example of response body:
I want to correlate at "rqUuid": "urn:uuid:1a5d8617-258c-49f7-b1a7-5b8ee71fb9fd" in the response body. Question is, is this the correct way to correlate the JSON Body? Do I need to correlate the response body although I already define the function "event_uuid": "${__UUID}" in the Body Data?
Thanks. Appreciate your help.
You are using a regular expression to get your data from a JSON response using the JSON Extractor. You need to use JSON Path Expressions instead of using regular expressions.
If you want to extract event_uuid from the response, your json path expressions would be events[*].event_uuid
To get the first event_uuid of your events array objects, you can use
events[0].event_uuid
JSON Extractor allows you executing JsonPath queries and it looks like you're trying to use a regular expression there, it will result into a syntax error, you can see jmeter.log file for details:
You're showing us request data and asking about extracting values from the response, in order to be able to help we need to see at least partial (or better full) response data and what part of it do you need.
So far I can only give the following piece of advice: switch to Regular Expression Extractor and there is a chance it will start working without any changes
You can use JSON Extractor or JSON JMESPath Extractor for extracting values from JSON responses.
Your JSON path expression should be responseHeader.rqUuid
You can evaluate the JSON Path expressions or JMESPath expression through the View Result tree or with online tools.
View Result Tree
You can generate the expressions online with http://jsonselector.com/
JMSE Path Evaluator https://jmespath.org
Sample JMX is uploaded to GitHub for your reference https://github.com/pragmatictesters/Pragmatic-Learning-JMeter-Examples/blob/master/TestPlan-StackOverFlow-68706730-JSON.jmx

Pact Consumer / Provider based in data type and not in data value

We are currently using Pact-Broker in our Spring Boot application with really good results for our integration tests.
Our tests using Pact-Broker are base in a call to a REST API and comparing the response with the value in our provider, always using JSON format.
Our problem is that the values to compare are in a DB where the data is changing quite often, which make us update the tests really often.
Do you know if it is possible to just validate by the data type?
What we would like to try is to validate that the JSON is properly formed and the data type match, for example, if our REST API gives this output:
[
{
"action": "VIEW",
"id": 1,
"module": "A",
"section": "pendingList",
"state": null
},
{
"action": "VIEW",
"id": 2,
"module": "B",
"section": "finished",
"state": null
}
}
]
For example, what we would like to validate from the previous output is the following:
The JSON is well formed.
All the keys / value pair exists based in the model.
The value match a specific data type, for example, that the key action exist in all the entries and contains a string data type.
Do you know if this is possible to be accomplished with Pact-Broker? I was searching in the documentation but I did not found any example of how to do it.
Thanks a lot in advance.
Best regards.
Absolutely! The first 2 things Pact will always do without any extra work.
What you are talking about is referred to as flexible matching [1]. You don't want to match the value, but the type (or a regex). Given you are using Spring Boot, you may want to look at the various matchers available for Pact JVM [2].
I'm not sure if you meant it, but just for clarity, Pact and Pact Broker are separate things. Pact is the Open Source contract-testing framework, and Pact Broker [3] is a tool to help share and collaborate on those contracts with the team.
[1] https://docs.pact.io/getting_started/matching
[2] https://github.com/DiUS/pact-jvm/tree/master/consumer/pact-jvm-consumer#dsl-matching-methods
[3] https://github.com/pact-foundation/pact_broker/

manipulating (nested) JSON keys and there values, using nifi

I am currently facing an issue where I have to read a JSON file that has mostly the same structure, has about 10k+ lines, and is nested.
I thought about creating my own custom processor which reads the JSON and replaces several matching key/values to the ones needed. As I am trying to use NiFi I assume that there should be a more comfortable way as the JSON-structure itself is mostly consistent.
I already tried using the ReplaceText processor as well as the JoltTransformJson processor, but I could not figure out. How can I transform both keys and values, if needed? For example: if there is something like this:
{
"id": "test"
},
{
"id": "14"
}
It might be necessary to turn the "id" into "Number" and map "test" to "3", as I am using different keys/values in my jsonfiles/database, so they need to fit those. Is there a way of doing so without having to create my own processor?
Regards,
Steve

Structuring json data in GET call query parameters

I'm trying to pass a list of the following objects as query params to a GET call to my Java service:
{
"id": "123456",
"country": "US",
"locale": "en_us"
}
As a url, this would like like
GET endpoint.com/entity?id1=123456&country1=US&locale1=en_us&id2=...
What's the best way to handle this as a service? If I'm passing potentially 15 of these objects, is there a concise way to take in these parameters and convert them to Java objects on the server side?
I imagine with a URL like this, the service controller would have a lot of #QueryParams...
Create the entire dataset as JSON array, e.g.
[
{
"id": "123456",
"country": "US",
"locale": "en_us"
},
{
"id": "7890",
"country": "UK",
"locale": "en_gb"
}
]
base64 encode it and pass it as a parameter, e.g.
GET endpoint.com/entity?set=BASE64_ENCODED_DATASET
then decode on the server and parse the JSON array into Java objects using perhaps Spring Boot.
Based on the valid URL size comment (although 2000 is usable), you could put the data in a header instead, which can be from 8-16kb depending on the server. GETting multiple resources at once is going to involve compromise somewhere in the design.
As Base64 can contain +/= you can url encode it too although I haven't found the need to do this in practice when using this technique in SAML.
Another approach would be to compromise on searching via country and locale specific IDs:
GET endpoint.com/entity/{country}/{locale}/{id_csv}
so you would search like this:
GET endpoint.com/entity/US/en_us/123456,0349,23421
your backend handles (if using Spring) as #PathParam for {country} and {locale} and it splits {id_csv} to get the list of IDs for that country/locale combination.
To get another country/locale search:
GET endpoint.com/entity/UK/en_gb/7890,234,123232
URLs are much smaller but you can't query the entire dataset in one go as you need to query based on country/locale each time.
It looks like your GET is getting multiple resources from the server. I'd consider refactoring to GET 1 resource from the server per GET request. If this causes performance issues, consider using HTTP caching.

Should we use enums in web json result

For example, I have a web api which return a Json Http respone Body. The fields in JSON is meaningful, but the question is should I use a string to describe it ? or use a int enum?
Example A:
{
"user_id": 123,
"sex": "male",
"status": "active"
}
Example B:
{
"user_id": 123,
"sex": 1,
"status": 1
}
which is better? and why?
maybe the Example can save some net flow?
This depends on a couple of things, mainly: How many times do these values appear in the JSON you're sending, and are you using compression?
If you're compressing the data you're sending using gzip or something similar, then the difference will be negligible.
The best way to find out is to try both approaches for your use case and meter the data usage, and see which one works better for you.