繁体   English   中英

在 SoapUI 中使用 groovy 数组动态比较 Rest XML/JSON 响应和 JDBC

[英]Dynamically compare Rest XML/JSON response and JDBC using groovy array in SoapUI

在 SoapUI 中,我有一个 JDBC 测试步骤,它返回以下数据:

<Results>
<ResultSet fetchSize="128">
    <Row rowNumber="1">
        <ID>1</ID>
        <NAME>TestName1</NAME>
        <DESCRIPTION/>
        <TYPE>Bool</TYPE>
        <ISPRODUCTTAG>true</ISPRODUCTTAG>
        <ISLOCATIONTAG>false</ISLOCATIONTAG>
        <SUBSECTION>Default Sub Section</SUBSECTION>
        <SECTION>Default Section</SECTION>
        <SUBGROUP>Default Sub Group</SUBGROUP>
        <GROUP>Default Group</GROUP>
    </Row>
    <Row rowNumber="2">
        <ID>2</ID>
        <NAME>TestName2</NAME>
        <DESCRIPTION/>
        <TYPE>Bool</TYPE>
        <ISPRODUCTTAG>true</ISPRODUCTTAG>
        <ISLOCATIONTAG>false</ISLOCATIONTAG>
        <SUBSECTION>Default Sub Section</SUBSECTION>
        <SECTION>Default Section</SECTION>
        <SUBGROUP>Default Sub Group</SUBGROUP>
        <GROUP>Default Group</GROUP>
    </Row>
    </Row>
</ResultSet>

我有一个包含以下数据的 REST API XML 响应:

    <ArrayOfTagInfo>
   <TagInfo id="1" name="TestName1" type="Bool" isProductTag="true" isLocationTag="false" subsection="Default Sub Section" section="Default Section" subgroup="Default Sub Group" group="Default Group"/>
   <TagInfo id="2" name="TestName2" type="Bool" isProductTag="true" isLocationTag="false" subsection="Default Sub Section" section="Default Section" subgroup="Default Sub Group" group="Default Group"/>
</ArrayOfTagInfo>

如果可能,我希望能够使用 groovy 数组比较(断言)数据库值和响应值(响应可以是 XML 或 JSON,具体取决于请求接受标头),因为从数据库返回的数据可能非常大.

任何人都可以帮忙吗?

如果你有 SoapUI-Pro,你应该能够在没有 Groovy 的情况下完成所有这些工作。

  1. 进行 REST 调用以检索所有数据。
  2. 启动解析 XML 的DataSource 步骤
  3. 进行 JDBC 调用以选择要验证的行的正确 ID。 在这里做出所有断言。
  4. 循环回到#2。

您可以使用以下测试步骤设计测试用例:

  1. jdbc步骤
  2. json步骤
  3. 常规脚本步骤

groovy 脚本步骤中的想法/sudo 代码是

  • 获取 jdbc 步骤的响应
  • 获取json步骤的响应
  • 以对象的形式构建数据,以便于比较
  • 将对象存储在列表中,一个用于 jdbc,另一个用于 json
  • 对两个列表进行排序,以确保比较相同的数据
  • 比较两个列表是否相同。

这是 groovy 脚本:

/**
 * Model object for comparing
 */
@groovy.transform.Canonical
class Model {
    def id
    def name
    def type
    def isProductTag
    def isLocationTag
    def subSection
    def section
    def subGroup
    def group

    /**
     * this will acception jdbc row
     * @param row
     * @return
     */
    def buildJdbcData(row) {
        row.with {
            id = ID
            name = NAME
            type = TYPE
            isProductTag = ISPRODUCTTAG
            isLocationTag = ISLOCATIONTAG
            subSection = SUBSECTION
            section = SECTION
            subGroup = SUBGROUP
            group = GROUP
        }
    }

    /**
     * this will accept the json TagInfo
     * @param tagInfo
     * @return
     */
    def buildJsonData(tagInfo){
        id = tagInfo.@id
        name = tagInfo.@name
        type = tagInfo.@type
        isProductTag = tagInfo.@isProductTag
        isLocationTag = tagInfo.@isLocationTag
        subSection = tagInfo.@subsection
        section = tagInfo.@section
        subGroup = tagInfo.@subgroup
        group = tagInfo.@group
    }
}

/**
 * Creating the jdbcResponse from the response received, using fixed value for testing
 * If you want, you can assign the response received directly using below instead of current and make sure you replace the step name correctly
 * def jdbcResponse = context.expand('${JdbcStepName#Response}')
 */
def jdbcResponse = '''<Results>
<ResultSet fetchSize="128">
    <Row rowNumber="1">
        <ID>1</ID>
        <NAME>TestName1</NAME>
        <DESCRIPTION/>
        <TYPE>Bool</TYPE>
        <ISPRODUCTTAG>true</ISPRODUCTTAG>
        <ISLOCATIONTAG>false</ISLOCATIONTAG>
        <SUBSECTION>Default Sub Section</SUBSECTION>
        <SECTION>Default Section</SECTION>
        <SUBGROUP>Default Sub Group</SUBGROUP>
        <GROUP>Default Group</GROUP>
    </Row>
    <Row rowNumber="2">
        <ID>2</ID>
        <NAME>TestName2</NAME>
        <DESCRIPTION/>
        <TYPE>Bool</TYPE>
        <ISPRODUCTTAG>true</ISPRODUCTTAG>
        <ISLOCATIONTAG>false</ISLOCATIONTAG>
        <SUBSECTION>Default Sub Section</SUBSECTION>
        <SECTION>Default Section</SECTION>
        <SUBGROUP>Default Sub Group</SUBGROUP>
        <GROUP>Default Group</GROUP>
    </Row>
    <!--added 3rd row for testing the failure -->
    <Row rowNumber="3">
        <ID>3</ID>
        <NAME>TestName3</NAME>
        <DESCRIPTION/>
        <TYPE>Bool</TYPE>
        <ISPRODUCTTAG>false</ISPRODUCTTAG>
        <ISLOCATIONTAG>false</ISLOCATIONTAG>
        <SUBSECTION>Default Sub Section3</SUBSECTION>
        <SECTION>Default Section3</SECTION>
        <SUBGROUP>Default Sub Group3</SUBGROUP>
        <GROUP>Default Group3</GROUP>
    </Row>
</ResultSet>
</Results>'''

/**
 * Creating the jsonResponse from the response received, using fixed value for testing
 * If you want, you can assign the response received directly using below instead of current and make sure you replace the step name correctly
 * def jsonResponse = context.expand('${JsonStepName#Response}')

 */
def restResponse = '''
<ArrayOfTagInfo>
   <TagInfo id="1" name="TestName1" type="Bool" isProductTag="true" isLocationTag="false" subsection="Default Sub Section" section="Default Section" subgroup="Default Sub Group" group="Default Group"/>
   <TagInfo id="2" name="TestName2" type="Bool" isProductTag="true" isLocationTag="false" subsection="Default Sub Section" section="Default Section" subgroup="Default Sub Group" group="Default Group"/>
  <!--added 3rd row for testing the failure -->
   <TagInfo id="3" name="TestName3" type="Bool" isProductTag="true" isLocationTag="false" subsection="Default Sub Section" section="Default Section" subgroup="Default Sub Group" group="Default Group"/>
</ArrayOfTagInfo>'''

//Parsing the jdbc and build the jdbc model object list
def results = new XmlSlurper().parseText(jdbcResponse)
def jdbcDataObjects = []
results.ResultSet.Row.each { row ->
    jdbcDataObjects.add(new Model().buildJdbcData(row))
}

//Parsing the json and build the json model object list
def arrayOfTagInfo = new XmlSlurper().parseText(restResponse)
def jsonDataObjects = []
arrayOfTagInfo.TagInfo.each { tagInfo ->
    jsonDataObjects.add(new Model().buildJsonData(tagInfo))
}

//sorting the Data before checking for equality
jdbcDataObjects.sort()
jsonDataObjects.sort()

if (jdbcDataObjects.size() != jsonDataObjects.size()) {
    System.err.println("Jdbc resultset size is : ${jdbcDataObjects.size()} and Json result size is : ${jsonDataObjects.size()}")
}
assert jdbcDataObjects == jsonDataObjects, "Comparison of Jdbc and Json data is failed"

在上面,第 3 行不匹配,因此 assert 将抛出以下错误:

捕获:java.lang.AssertionError:比较失败。 表达式:(jdbcDataObjects == jsonDataObjects)。 值:jdbcDataObjects = [默认组 3,默认组,默认组],jsonDataObjects = [默认组,默认组,默认组] java.lang.AssertionError:比较失败。 表达式:(jdbcDataObjects == jsonDataObjects)。 值:jdbcDataObjects = [默认组 3,默认组,默认组],jsonDataObjects = [默认组,默认组,默认组] 在 So31472381.run(So31472381.groovy:104)
进程以退出代码 1 结束

如果删除 3rd(从两个响应中),则不会看到任何错误,这表明 jdbc 和 json 响应的比较成功。

请注意,免费版和专业版的SoapUI都提供groovy script 所以这个解决方案适用于 SoapUI 的两个版本。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM