Search code examples
jsonrestgroovysoapuijsonslurper

Number Format Exception in Groovy


I am trying to compare the Sales Tax Rate of 6.75 against my expected value of 6.75 which is in string format. I wrote the below lines of Groovy code to achieve this, but I am getting Number Format Exception and I could not figure out where the problem is

Groovy Code

def jsonSlurper = new JsonSlurper()
def parsedResponseJson=jsonSlurper.parseText(context.expand('${StandardFinance#Response}'))
def actualSalesTaxRate = parsedResponseJson.CustomerQuoteFinanceResponse.StandardFinanceResponse.Responses[0].StandardPaymentEngineFinanceResponse.paymentWithTaxes.financeItemizedTaxes.salesTax.taxParameters.rate
def actualSalesTaxRate = parsedResponseJson.CustomerQuoteFinanceResponse.StandardFinanceResponse.Responses[0].StandardPaymentEngineFinanceResponse.paymentWithTaxes.financeItemizedTaxes.salesTax.taxParameters.rate
log.info actualSalesTaxRate.size()
actualSalesTaxRate = Float.parseFloat(actualSalesTaxRate)
def expectedSalesTaxRate = "6.75"
log.info expectedSalesTaxRate.size()
expectedSalesTaxRate = Float.parseFloat(expectedSalesTaxRate)
assert expectedSalesTaxRate.toString() == actualSalesTaxRate.toString(),"FAIL --- Sales Tax Rate is different"

JSON Response

{
"CustomerQuoteFinanceResponse": {
    "StandardFinanceResponse": {
        "Responses": [{
            "StandardPaymentEngineFinanceResponse": {
                "class": ".APRNonCashCustomerQuote",
                "RequestID": "1",
                "term": "48",
                "financeSourceId": "F000CE",
                "paymentWithTaxes": {
                    "class": ".FinancePaymentWithTaxes",
                    "amountFinanced": "34523.48",
                    "monthlyPayment": "782.60",
                    "monthlyPaymentWithoutDealerAddOns": 782.6,
                    "financeItemizedTaxes": {
                        "salesTax": {
                            "taxParameters": {
                                "rate": "6.75"
                            },
                            "salesTaxAmount": "2322.61"
                        }
                    }
                }
            }
        }]
    }
}
}

Solution

  • You do not have to convert it to number as the value in the response is string.

    • define a test case level custom property say EXPECTED_TAX_RATE and provide the value as 6.75.
    • in the response, the rate is a string value.
    • there is no need to create an additional Groovy Script test step in this particular case just to check/compare the value, remove step.
    • instead, add Script Assertion for the rest request test step itself with above code.
    • however, there is small change need to read the response.

    Here is the complete Script Assertion

    //Check the response is received
    assert context.response, 'Response is empty or null'
    
    //Read test case property for expected value as string; this way there is no need to edit the assertion; just change the property value
    def expectedTaxRate = context.expand('${#TestCase#EXPECTED_TAX_RATE}')
    
    def json = new groovy.json.JsonSlurper().parseText(context.response)
    
    def actualTaxRate = json.CustomerQuoteFinanceResponse.StandardFinanceResponse.Responses[0].StandardPaymentEngineFinanceResponse.paymentWithTaxes.financeItemizedTaxes.salesTax.taxParameters.rate
    log.info "Actual tax rate $actualSalesTaxRate"
    
    //Now compare expected and actual
    assert actualTaxRate == expectedTaxRate, 'Both tax rates are not matching'
    

    You may have question such as "Leave about string values. How to compare with Numbers. For example monthlyPaymentWithoutDealerAddOns is having number not string. How to deal with it?"

    Here when a test case level custom property is defined as EXPECTED_MONTHLY_PATYMENT and value as 782.6.

    Like it is already mentioned the above can be read in Script Assertion as below

    def expectedMonthlyPayment = context.expand('${#TestCase#EXPECTED_MONTHLY_PATYMENT}') //but this is string
    

    You can read actual value as:

    def actualPayment = json.CustomerQuoteFinanceResponse.StandardFinanceResponse.Responses[0].StandardPaymentEngineFinanceResponse.paymentWithTaxes.monthlyPaymentWithoutDealerAddOns
    log.info actualPayment.class.name //this shows the data type
    

    Now expectedPayment needs to be converted to actualPayment's type

    def actualPayment = json.CustomerQuoteFinanceResponse.StandardFinanceResponse.Responses[0].StandardPaymentEngineFinanceResponse.paymentWithTaxes.monthlyPaymentWithoutDealerAddOns
    log.info actualPayment.class.name //this shows the data type
    def expectedPayment = context.expand('${#TestCase#EXPECTED_MONTHLY_PATYMENT}') as BigDecimal
    assert actualPayment == actualPayment