I'm trying to extract the header from a previous request in SoapUI so I can use it in another request. Basically, I want to get the node value for Header in one xml and insert it into the header value of another xml. I have tried using XMLSlurper and XMLParser but not getting exactly what I want. I can extract out the text from the nodes but need the actual whole header value so it can be inserted into other requests as needed.
text = testRunner.testCase.testSteps["ConversionRate"].testRequest.response.getRequestContent()
log.info text
def slurped = new XmlSlurper().parseText(text)
log.info slurped.Header
This results in Value1Value2 using the XML example below but I want to extract out the whole header so it looks like
<soapenv:Header>
<soapenv:MyTag>value1</soapenv:MyTag>
<soapenv:MyTag2>value2</soapenv:MyTag2>
</soapenv:Header>
Sample XML for the purpose of this question is below
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:web="http://www.webserviceX.NET/">
<soapenv:Header>
<soapenv:MyTag>value1</soapenv:MyTag>
<soapenv:MyTag2>value2</soapenv:MyTag2>
</soapenv:Header>
<soapenv:Body>
<web:ConversionRate>
<web:FromCurrency>AFA</web:FromCurrency>
<web:ToCurrency>ALL</web:ToCurrency>
</web:ConversionRate>
</soapenv:Body>
</soapenv:Envelope>
Once I have the value I will need to insert it into the header as an xml sample such as below
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:web="http://www.webserviceX.NET/">
<soapenv:Header/>
<soapenv:Body>
<web:ConversionRate>
<web:FromCurrency>AFA</web:FromCurrency>
<web:ToCurrency>ALL</web:ToCurrency>
</web:ConversionRate>
</soapenv:Body>
</soapenv:Envelope>
Hope this makes sense and any suggestions on how to get the node value for Header in xml and insert it into the header value of another xml would be very appreciated
Thanks
Based on the comments, adding the below as answer. And this is completely different solution from the other one.
- This is a script assertion for first request test step
- You do not have to define the element names unlike the other solution
- The script automatically reads the headers from the first request and creates a map of element name and its value
- This also reads next test step request and adds the above step map data as headers into the xml
- Updates the changes xml to next test step request.
Here is the Script Assertion (for the first test step): You may also follow the in-line comments.
//Edit the name of the next test step name if required
def nextStepName = 'SOAP Request2'
//Check if the current request is empty
assert context.request, 'Request is empty or null'
def nextStep = context.testCase.testSteps[nextStepName]
log.info "Next step request before edit: ${nextStep.testRequest.requestContent}"
def getXml = { req -> new XmlSlurper().parseText(req) }
def getRequestHeaderMap = { x ->
def header = x.'**'.find {it.name() == 'Header'}
header.children()*.name().collectEntries {[(it): header."$it".text()]}
}
//Read and Parse current request and get headers as map
def currentRequestHeaders = getRequestHeaderMap(getXml(context.request))
log.info "Current request header parameters : $currentRequestHeaders"
//Read and Parse next step request
def nextRequest = getXml(nextStep.testRequest.requestContent)
//Remove existing headers
nextRequest.Header.replaceBody {}
//Update next request xml with current request headers
currentRequestHeaders.collect { k, v -> nextRequest.Header.appendNode { "ns11:$k"('xmlns:ns11': 'http://schemas.xmlsoap.org/soap/envelope/', v) } }
def nextRequestString = groovy.xml.XmlUtil.serialize(nextRequest)
log.info "Updating next request with : $nextRequestString"
//Update next test step's request content
nextStep.testRequest.requestContent = nextRequestString
You do not have use an addition groovy script to achieve the same. Instead add Script Assertion
with the below code for the first SOAP request test step.
Script: follow in-line comments
//Define your element names to extract the data
def elements = ['MyTag', 'MyTag2']
//Don't modify anything beyond this point
//Check if the request is empty
assert context.request, 'Request is empty or null'
//Parse response
def xml = new XmlSlurper().parseText(context.request)
//Closure to find the element data
def getData = { element -> xml.'**'.find {it.name() == element}?.text() }
//Find the tag value and set the same as
elements.each { context.testCase.setPropertyValue(it, getData(it)) }
Make the following change in the next request where you wanted to add the headers. Note the headers and property expansions.
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:web="http://www.webserviceX.NET/">
<soapenv:Header>
<soapenv:MyTag>${#TestCase#MyTag}</soapenv:MyTag>
<soapenv:MyTag2>${#TestCase#MyTag2}</soapenv:MyTag2>
</soapenv:Header>
<soapenv:Body>
<web:ConversionRate>
<web:FromCurrency>AFA</web:FromCurrency>
<web:ToCurrency>ALL</web:ToCurrency>
</web:ConversionRate>
</soapenv:Body>
</soapenv:Envelope>