Ask a Question

XPATH assertion for an expression containing another value, field length, field type and is not NULL

SOLVED
cstott1
Occasional Contributor

XPATH assertion for an expression containing another value, field length, field type and is not NULL

Hi,

 

I have used a JDBC driver to run a SQL query. The below is the result

 

<Results>
    <ResultSet fetchSize="128">
        <Row rowNumber="1">
            <PIECEID>1820480</PIECEID>
            <CONSIGNMENTID>1166645</CONSIGNMENTID>
            <TRACKINGNUMBER>907598985733</TRACKINGNUMBER>
            <BARCODE>001390759898573373</BARCODE>
            <ISBILLABLE>1</ISBILLABLE>
            <ISCANCELLED>0</ISCANCELLED>
        </Row>
    </ResultSet>
</Results>

 

I am trying to setup 4 assertions for the below but am struggling with what to put in the expected result.

 

1) <BARCODE> contains the <TRACKINGNUMBER>

2) <ISCANCELLED> is not NULL

3) <PIECEID> is 7 digits long

4)  <ISBILLABLE> is numerical

 

Also being very new to  XPATH where is the best place to learn it for the purposes of expected results in SOAPUI

8 REPLIES 8
cstott1
Occasional Contributor

Hi,

 

I have used a JDBC driver to run a SQL query. The below is the result

 

<Results>
    <ResultSet fetchSize="128">
        <Row rowNumber="1">
            <PIECEID>1820480</PIECEID>
            <CONSIGNMENTID>1166645</CONSIGNMENTID>
            <TRACKINGNUMBER>907598985733</TRACKINGNUMBER>
            <BARCODE>001390759898573373</BARCODE>
            <ISBILLABLE>1</ISBILLABLE>
            <ISCANCELLED>0</ISCANCELLED>
        </Row>
    </ResultSet>
</Results>

 

I am trying to setup 4 assertions for the below but am struggling with what to put in the expected result.

 

1) <BARCODE> contains the <TRACKINGNUMBER>

2) <ISCANCELLED> is not NULL

3) <PIECEID> is 7 digits long

4)  <ISBILLABLE> is numerical

 

Also being very new to  XPATH where is the best place to learn it for the purposes of expected results in SOAPUI? Is XQUERY what i should learn for this?

nmrao
Champion Level 3

I believe script assertion suites better fit in this case.


Regards,
Rao.
cstott1
Occasional Contributor

Many thanks Rao, i will check that out. To get me started what scripts would you put for those 4 examples?

nmrao
Champion Level 3

Below groovy script does what you needed.

 

It is taken one positive Row and a negative Row for the sake of test evaluation.

 

/**
* this class holds the all 4 assertions result along with its rowNumber
**/
class AssertionResult {
  def rowNumber
  def failures
}

/**
* below method will validates each row and returns AssertionResult object
**/
def validateRow(row) {
   def number = row.@rowNumber
   def barCode = row.BARCODE.text()
   def trackingNumber = row.TRACKINGNUMBER.text()
   def tempResult = new AssertionResult(rowNumber: number, failures: null)
   StringBuffer tempFailure = new StringBuffer()
   if (!barCode.contains(trackingNumber)) {
      tempFailure.append("Bar code does not contain Tracking number\n")
   }
   if (!row.ISCANCELLED.text()) {
      tempFailure.append("Is cancelled empty\n")
   }
   if (!(row.PIECEID ==~ "\\d{7}")){
      tempFailure.append("PieceId is not of 7 digits long\n")
   }
   def billable
   try { 
       billable = row.ISBILLABLE.text() as Long
       if (!(billable instanceof java.lang.Long)) {
           tempFailure.append("Is billable is not a number\n")
       }
   } catch (NumberFormatException e) {
      tempFailure.append("Is billable is not a number\n")
   }   
   if (tempFailure) {
      tempResult.failures = tempFailure.toString()
   }
   tempResult
}


/**
* below is the sample result set
* you may directly assign the response from jdbc test step here later
**/
def jdbcResponse = '''
<Results>
    <ResultSet fetchSize="128">
        <Row rowNumber="1">
            <PIECEID>1820480</PIECEID>
            <CONSIGNMENTID>1166645</CONSIGNMENTID>
            <TRACKINGNUMBER>907598985733</TRACKINGNUMBER>
            <BARCODE>001390759898573373</BARCODE>
            <ISBILLABLE>1</ISBILLABLE>
            <ISCANCELLED>0</ISCANCELLED>
        </Row>
        <Row rowNumber="2">
            <PIECEID>18204811</PIECEID>
            <CONSIGNMENTID>1166646</CONSIGNMENTID>
            <TRACKINGNUMBER>907598985734</TRACKINGNUMBER>
            <BARCODE>001390759898573375</BARCODE>
            <ISBILLABLE>a</ISBILLABLE>
            <ISCANCELLED/>
        </Row>
    </ResultSet>
</Results>'''
def results = new XmlSlurper().parseText(jdbcResponse)
def assertionResults = []

/**
* looping thru each Row and validating the row data and 
* collecting result into a list
**/
results.ResultSet.Row.each {
   assertionResults.add(validateRow(it))
}

/**
* check the validation result and log errors if any
* and then finally show if the resultset data is passed the 
* mentioned 4 conditions or not
**/
def finalResult = true
assertionResults.each { res ->
  if (res.failures) {
    finalResult = false
    log.error "Row number ${res.rowNumber} has assertion errors:\n ${res.failures}"
  }
}

assert finalResult, "The data verification on ResultSet has failures as logged above"
​

Note: The reason for using if conditions in validateRow() method becuase, it will stop the assertions on first failure and rest of the verification is not done. 

 

You may see error something like shown below

JdbcVerificationJdbcVerification

 



Regards,
Rao.
nmrao
Champion Level 3

You may use the above code either in script assertion(it will not be a separate step) or as a groovy script (a separate test step)


Regards,
Rao.
nmrao
Champion Level 3

By the way I like the way you explained the question clearly.
May be that demanded me to attempt validating a jdbc resultset for first time and looping it in groovy script. Thank you for the question.



Regards,
Rao.
cstott1
Occasional Contributor

Perfect, many thanks for your help

cstott1
Occasional Contributor

 Hi Rao, I have tried to write this for one field in the way below:

 

def pieceid = context.expand( '${OneDX#ResponseAsXml#//Results[1]/ResultSet[1]/Row[1]/PIECEID[1]}' )

def TrackingNumber = context.expand( '${OneDX#ResponseAsXml#//Results[1]/ResultSet[1]/Row[1]/TRACKINGNUMBER[1]}' )

 

assert {!TrackingNumber.contains(Pieceid)}

 

The tracking number is 907598985733 and Pieceid is 1820480....therefore the Pieceid is not in the tracking number. However when I run the script it passes. do you know what i'm doing wrong

cancel
Showing results for 
Search instead for 
Did you mean: