ERROR c.k.k.core.keyword.internal.KeywordMain - ? Expected text is 'Approved' but actual element text is:
I will report what I have found out later.
Reading the source code, I found that the source code of Katalon Studio is careless about the XML Namespace. Therefore now I think that Katalon Studio is not good for testing SOAP services. I think, you had better look at other test tools which have good reputation for testing SOAP services.
You should avoid the builtin WS.verifyElementText keyword as long as your XML contains <env:Header> element.
In Katalon Studio, you can get access to the XML response body, parse it and extract text content out of the XML elements; then you can make assertions: do these by your Groovy scripts (Test Case and Custom Keywords)
By the way, I looked at other API Testing tool Postman. I found that you have to write a bunch of custom codes (in Node.js) to process and verify SOAP messages in Postman. Now a question to you would be; which tool (which scripting language) you like?
Here is a sample Test Case script that can verify your XML Response.
I just wanted to let Katalon Team be aware that the WS.verifyElementText keyword is problematic, it is confusing more and more people, it requires some fix. I just hope Katalon Team to address this issue.
=============== ROOT CAUSE =====================
For trouble shooting, please visit: https://docs.katalon.com/katalon-studio/docs/troubleshooting.html
09-21-2021 06:37:57 PM verifyElementText(strippedResponse, "PreAuthorizeResponse.Receipt.TransactionResult", "Approved")
Elapsed time: 0.334s
Unable to verify element text (Root cause: com.kms.katalon.core.exception.StepFailedException: Expected text is 'Approved' but actual element text is:
at com.kms.katalon.core.webservice.keyword.WSBuiltInKeywords$verifyElementText$0.call(Unknown Source)
at com.kms.katalon.core.main.TestCaseMain$runTestCase$0.call(Unknown Source)
This is an issue that KS doesn’t recognize namespace in SOAP Envelope Body. It was planned to fix in KS v8.2.0 that will release in Nov 18th.
The workaround, for now, is to copy the folder Include/scripts/groovy of the attachment project and paste it to the user’s project. If everything is OK, they can see the added scripts look like the image below:
The document MUST clearly describe why it applies the magical XPath //*//*//*. What is the intension. What this keyword assumes the response text to be like.
I believe the programmer who wrote the WS.verifyElementText() keyword implicitly assumed that, in case the response is a XML, the document is a SOAP <env:Envelope> with a <env:Body> element and without a<env:Head> element. The keyword fails to process a SOAP message with an <env:Head> element, Also this keyword fails to process non-SOAP messages.
The name of the keyword “verifyElementText” is not appropriate. The name “verifyElementText” sounds generic. The name sounds as if the keyword would solve every problems. But actually the keyword is narrow scoped. It does not support non-SOAP XML messages. The keyword should rather be called “verifySOAPBodyElementTextInCaseOfSOAPMessageWithoutHead” to express what it does.
The above experiment shows that the ReponseObject.getResponseBodyContent() returns
the descendant nodes of <env:Body> element of the Response text when the response text does NOT have <env:Head> element.
the descendant nodes of <env:Head> element of the Response text when the response text has a <env:Head> element.
I feel this behaviour is very strange. It is difficult to see why ResponseObject.getResponseBody() behaves like this. I suppose that it should rather return the the descendant nodes of <env:Body> element of the Response text regardless if the response text has a <env:Head> element or not. — But in fact, this is not the case.
This behaviour of ResponseObject.getResponseBody() affects WS.verifyElementText().
I think that, regardless if this behaviour is as intended or not, the document of WS.verifyElementText() MUST describe the keyword will behave as this.
So, I think that the author wrote the magical XPath //*//*//* intending to select the child node set of a SOAP <env:Body> element. But he carelessly neglected the case where the SOAP message contains a <env:Head> element preceding to the <env:Body>. This was his mistake.
XML data are similar both in the structure and the way we define element locator , our expected info may come from: the attribute of XML tag (in example below, " no" is an attribute of " contacts" tag) or from inner child tag, you can use keywords for handling text (e.g. verifyElementText) or property (e.g. verifyElementPropertyValue) respectively.
I think that the former locator is mysterious. Why Envelope element and Body element are skipped in the locator? It it right or not?
I think that the latter locator is intuitive and definitive. Here I should write an absolute GPath starting from the Document root (Envelope) going down the layers of nodes (Body.GetEmployeeResponse.employee.contacts) to the element of my interest(email). I find no mystery here.
I got confused: Which way the keyword requires? I read the official document, but it does not answer to my question.
Therefore I would argue that users should not use the WS.verifyElementText() keyword for XML because of the poor documentation.
2021-10-08 18:36:01.105 ERROR c.k.k.core.keyword.internal.KeywordMain - ❌ Expected text is 'Approved' but actual element text is: Approved
2021-10-08 18:36:01.122 ERROR c.k.k.core.keyword.internal.KeywordMain - ❌ Unable to verify element text (Root cause: com.kms.katalon.core.exception.StepFailedException: Expected text is 'Approved' but actual element text is: Approved
This example shows that the WS.verifyElementText() keyword is difficult to use. It checks if the XML element content text is strictly equal to the 3rd argument string. Any NEWLINEs and whitespace characters easily break the equality test. Unfortunately the keyword offers no way to make the verification tolerant of whitespaces.
The official documentation explains nothing about the strictness for whitespaces. I am afraid that many people would get stuck with it.
Therefore I would still argue, users should not rely on this keyword. They should rather parse the XML in the Web Service Response themselves to look up elements of their interest while trimming (or ignoring) whitespaces in the content text as appropriate.