I try to substitute session variable in the request payload, and it doesn't work,
I am reading from csv file
empNo, orderNo
74726,[49 50]
71696,[52 51 53 50 37 36 38]
object BidSubmission extends HttpUtil {
val orders_feeder = csv("data/Round-1.csv").circular
def orderSubmission: ChainBuilder =
pause(pauseBy(5) seconds)
.repeat(1) {
feed(orders_feeder)
.exec(postToUri(s"${Constants.orderSubmission_URL}/#{$AuctionId}/base-orders/proxy-bid", "")
.queryParam("employeeId", "#{empNo}")
.body(StringBody(session => {
println(session)
println(session.attributes("empNo"))
val empNo = session.attributes("empNo").asInstanceOf[String]
val orderNo = session.attributes("orderNo").asInstanceOf[String]
println(s"\n\n\n $orderNo \n\n\n")
var slotNos = orderNo.replace("[", "").replace("]", "").split(" +")
println(s"\n\n\n ${generatePayload(empNo, slotNos)} \n\n\n")
generatePayload(empNo, slotNos)
" "
}))
)
}
private def generatePayload(empNo: String, orderNo: Array[String]) = {
s"""
| {
| "submittedAt": ${DateTimeFormatter.ISO_OFFSET_DATE_TIME.format(OffsetDateTime.now)}
| "allowSameMonth": false,
| "allowConsecutiveMonths": true,
| "selections": [
${generateSlotNo(orderNo)}
| ]
|}
|""".stripMargin
}
private def generateSlotNo(orderNo: Array[String]) = {
orderNo.map(slotNo => s"\"${Constants.proxySubmission_URL}/#{$AuctionId}/base-orders/00000-00000-00000/order-slots/${slotNo}\"").mkString(",")
}
}
AuctionId session variable is printed in the log, however it is not assigned inside the generateSlotNo method.
in generateSlotNo, AuctionId value is not substituted. It actually prints #{AuctionId} as it is, Can you please help me what i am missing here?
{
"submittedAt": 2023-02-12T22:51:47.860567-06:00
"allowSameMonth": false,
"allowConsecutiveMonths": true,
"selections": [
"https://service.east.cbna.dev1.dev.aws.swacorp.com/golden/base-auction/crew/auctions/#{AuctionId}/base-auctions/0da65bd8-a25f-4b2c-b2f6-2a7f5b0f6432/bid-slots/49","https://service.east.cbna.dev1.dev.aws.swacorp.com/golden/base-auction/crew/auctions/#{AuctionId}/base-auctions/0da65bd8-a25f-4b2c-b2f6-2a7f5b0f6432/bid-slots/50"
]
}
Can you please tell me how i can capture the post request - URI in the test? ie the URI that we are sending the post request to.
As explained in the documentation, Gatling Expression Language only works in Strings passed to Gatling DSL methods.
You can't use it in your own custom code, so you have to explicitly pass the value you want for AuctionId in generateSlotNo.
Related
I have a response that looks this
{
"metadata": {
"Customer_x0020_Folder": "Test"
}
}
I would like the assert key Customer_x0020_Folder is equal to 'Test'. However I don't care about the x0020 portion of they key and would like to ignore that part. I would like to do something like:
match response contains { metadata: {'Customer_' + '#ignore' + '_Folder': 'Test'} }
How can I perform this assertion in Karate?
Use karate.keysOf():
* def response = { "metadata": { "Customer_x0020_Folder": "Test" } }
* def keys = karate.keysOf(response.metadata)
* match keys[0] == '#regex Customer_.*_Folder'
I have a Json response like below. The difference here is my Json body has a number as the parent node.
def response =
"""
{
"22388043":[
{
"firstName":"Romin",
"lastName":"Irani",
"phoneNumber":"408-1234567",
"emailAddress":"romin.k.irani#gmail.com"
}
]
}
"""
I want to return the mobileNumber attribute value from the response body. In this scenario I don't have that attribute in my response. So here I want to get a null value.
So when I use * def mobile = $.22388043[0].mobileNumber, I'm getting below error.
No results for path: $['22388043'][0]['mobileNumber']
Please advise on this.
Karate does give you a way to get the values of JSON keys.
Hopefully this example answers all your other questions as well:
* def response =
"""
{
"22388043":[
{
"firstName":"Romin",
"lastName":"Irani",
"phoneNumber":"408-1234567",
"emailAddress":"romin.k.irani#gmail.com"
}
]
}
"""
* def id = karate.keysOf(response)[0]
* match id == '22388043'
* def person = response[id][0]
* match person contains { firstName: 'Romin', lastName: 'Irani' }
* match person.mobileNumber == '#notpresent'
I have the following feature file that reads the input and appends the input id with the response and writes to a text file in the below format:
|123|{"products": [ { "pid": "1a"} ] }|
|124|{"products": [ { "pid": "1b"} ] }|
|125|{"products": [ { "pid": "1c"} ] }|
so that I can make the input table with it and dont need copy each response in text format and paste to make Examples:
I have tried the below:
Feature: sample karate test script
Background:
* url BaseUrl
* configure headers = read('classpath:headers.js')
* def jsonFromCsv = read('data.csv')
* def size = karate.sizeOf(jsonFromCsv)
* print size
Scenario Outline: Get All Tests
* def doStorage =
"""
function(args) {
var DataStorage = Java.type('DataStorage.DataStorage'); // Java class that writes to a text file
var dS = new DataStorage();
return dS.write(args);
}"""
Given path '/v1/path'
When method get
Then status 200
* def json = __row.expected
* def id = __row.id
* def app = '|'+<id>+'|'+json+'|'
* print app # prinst it in the expected format
* def result = call doStorage app
Examples:
| jsonFromCsv |
But the issue is only the last read data is being written to the file.
I had tried the below as well but gives the same result as above:
* def js = function (app){karate.write(app,'input.txt')}
DataStorage.java:
package DataStorage;
import java.io.*;
public class DataStorage {
public void write( String text) throws IOException {
BufferedWriter output = null;
try {
File file = new File("input");
output = new BufferedWriter(new FileWriter(file));
output.append(text);
output.close();
} catch ( IOException e ) {
e.printStackTrace();
} finally {
if ( output != null ) {
output.close();
}
}
}
}
You can use CSV files (have to be comma delimited): https://github.com/intuit/karate#csv-files
Also see this example:
Scenario Outline: cat name: <name>
Given url demoBaseUrl
And path 'cats'
And request { name: '<name>', age: <age> }
When method post
Then status 200
And match response == { id: '#number', name: '<name>' }
# the single cell can be any valid karate expression
# and even reference a variable defined in the Background
Examples:
| read('kittens.csv') |
def userName = 'ABC'
def input json = {
"integration": {
"serviceData": {
"integrationService": {
"name": "fld_<tenantID>_stage00.integrations:<integrationName>"
},
"gitComments": "Commit made by: ABC"
}
}
}
In the above json I need to parameterize the user name 'ABC'
If I send
"gitComments": "#(userName)"
It is checking 'ABC' which is fine
But I need to prefix the String "Commit made by: " And then #(userName) in the input json.
Thanks in Advance
https://github.com/intuit/karate#rules-for-embedded-expressions
* def gitComments = 'Commit made by: ' + userName
* def json = { gitComments: '#(gitComments)' }
I have a Json payload to validate. And It has a property which can be either null or a sub json object. But this property exists in the json.
I tried following methods:
01
And def dnyAssertionSchema = { denyAny: '#boolean', assertions: '##[]' }
And match each policyGResponse ==
"""
{
denyAssertions: '##(dnyAssertionSchema)'
}
"""
AND
And match each policyGResponse ==
"""
{
denyAssertions: '##null dnyAssertionSchema'
}
"""
AND
This does not work as the property is not an array so I tried above second method even I couldn't find an example as such.
And match each policyGResponse ==
"""
{
denyAssertions: '##[] dnyAssertionSchema'
}
"""
The Actual response can be either
{
denyAssertions=null
}
OR
{
denyAssertions={ denyAny: true, assertions: ["a","b"] }
}
I use Karate 0.9.1
Error message I get is 'reason: actual value has 1 more key(s) than expected: {denyAssertions=null}' in first try
In second try I get 'assertion failed: path: $[3].denyAssertions, actual: {denyAny=false, assertions=[]}, expected: '##null dnyAssertionSchema', reason: not equal'
Your JSON is still not valid but anyway. Here you go:
* def schema = { denyAny: '#boolean', assertions: '#[]' }
* def response1 = { denyAssertions: { denyAny: true, assertions: ["a","b"] } }
* match response1 == { denyAssertions: '##(schema)' }
* def response2 = { denyAssertions: null }
* match response1 == { denyAssertions: '##(schema)' }