Forum Discussion

jkrier's avatar
jkrier
Regular Contributor
11 years ago

How do I Loop test steps inside of a test suite?

I've read many different posts on loops but none of them seem to do exactly what I am looking for. I have a test suite with many different test steps. At some point I am trying a Groovy script to create a while condition that will run some previous test steps so many times and then continue on. I have tried the following different methods and they either loop continuously or they run the test step that I want but then return back to the script or it might iterate correctly the first run through but subsequent runs don't seem to hit the loop at all.

This method will loop continuously
def loop = 1
log.info loop
while (loop < 2){ //must match if loop
log.info "Still Running " + loop
testRunner.gotoStepByName("getUniqueExternalReferenceValues 2")
loop = loop + 1
}




This method will not loop at all but when I run it in the Groovy test step manually it says it's going to the correct steps in the correct order.
def loop = 1
log.info loop
while (loop < 2){ //must match if loop
log.info "Still Running " + loop
testRunner.gotoStepByName("getUniqueExternalReferenceValues 2")
loop = loop + 1
}

if (loop == 2){ //must match while loop
testRunner.gotoStepByName("getUniqueExternalReferenceValues 3")
loop = 0
log.info "ALL DONE "+loop
}


And this method i've tried running it a few different ways but the results are just like the above examples

if( context.loopIndex == null )
context.loopIndex = 0
log.info context.loopIndex
while( context.loopIndex < 2 ){ //number of times to run loop
//log.info context.loopIndex
testRunner.gotoStepByName( "getUniqueExternalReferenceValues 2" ) //name of step to go to
context.loopIndex = context.loopIndex + 1
log.info context.loopIndex
}if ( context.loopIndex == 2 ){
context.loopIndex = 0
log.info context.loopIndex
testRunner.runTestStepByName("getUniqueExternalReferenceValues 3")

log.info context.loopIndex
}
}

In case it is not clear this is what I want to accomplish

1. Run Test Step 1
2. Run Test Step 2
3. Run Test Step 3
4. Run Test Step 4
5. Run Test Step 5
6. Run Test Step 6
7. Hit Groovy loop (Begin Loop)
8. Run Test Step 5
9. Run Test Step 6
10. Hit Groovy Loop (End Loop)
11. Run Test Step 7
  • jkrier's avatar
    jkrier
    Regular Contributor
    I figured out how to do this but it seems absurd that it must be done this way. You have to list out all of the steps between the loop and the start of the steps the loop is set to go back to. When you run this at the suite level it works fine, if you run this manually inside of the Groovy script step it loops continuously. The opposite of the behavior I noticed in one of my examples that, to me looks more appropriate than what actually ends up working. I also noticed that without the sleep some of the steps can step on each other.

    def loop = 1
    log.info loop
    while (loop < 2 ){ //must match if loop
    log.info "Still Running " + loop
    //You have to explicitly list all steps to run between the loop script and the test step loop start
    testRunner.runTestStepByName("getUniqueExternalReferenceValues 2")
    sleep 700
    testRunner.runTestStepByName("getTransitionPackages")
    sleep 700
    testRunner.runTestStepByName("TransitionProps")
    sleep 700
    testRunner.runTestStepByName("UpdateService_TransitionServiceItem")
    sleep 700
    testRunner.runTestStepByName("getSoaTransactionsByExternalAccountReference 3")
    sleep 700
    testRunner.runTestStepByName("checkTransitionStatus")
    sleep 700
    testRunner.runTestStepByName("TransitionVariables")
    sleep 700
    loop = loop + 1
    }

    if (loop == 2){ //must match while loop
    testRunner.gotoStepByName("getUniqueExternalReferenceValues 3")
    loop = 0
    log.info "ALL DONE "+loop
    }
    • andresmjc's avatar
      andresmjc
      New Contributor

      This helped me out tremendously after searching through many posts.  Did you ever get your issues resolved. My issue is that the script I wrote  loops and calls itself. after it loops one time. it does go on to the next steps but the original script step fails. 

      • jkrier's avatar
        jkrier
        Regular Contributor

        This was a long time ago, I don't even remember why I needed this functionality anymore. I was messing with the script and it seems to be running without any issues.

         

         

        def loop = 0
        log.info loop
        while (loop <= 2 ){ //must match if loop
        log.info "Still Running " + loop
        //You have to explicitly list all steps to run between the loop script and the test step loop start
        testRunner.runTestStepByName("Step1")
        sleep 700
        testRunner.runTestStepByName("Step2")
        sleep 700
        loop = loop + 1
        }
        
        log.info 'Loop End'
        testRunner.gotoStepByName("End Loop")

         

        There might be a better way to accomplish this by using the step indexes. Get the current step (Groovy loop script) index and just run so many, you could add a counter and do something like testRunner.runTestStepByName("Step" + stepIndex)

  • JHunt's avatar
    JHunt
    Community Hero

    If you want a variable to persist outside of an individual script, you can set it into the WsdlTestRunContext. Make sure you are running the TestCase, rather than just running the script in the editor.

     

    assert context instanceof com.eviware.soapui.impl.wsdl.testcase.WsdlTestRunContext
    assert testRunner instanceof com.eviware.soapui.impl.wsdl.testcase.WsdlTestCaseRunner

    int maxRuns = 2
    if (!context.runCount) context.runCount = 1

    if (context.runCount++ >= maxRuns) {
    return
    } else {
    testRunner.gotoStepByName("Some earlier TestStep")
    return
    }

     

    Context is a type of Map, so the above is essentially doing this:

     

    int count = 1
    if (context["runCount"] == null) {
    context += ["runCount": count]
    }

    Specifically, it is a StringToObject map, so you can put any variable you want into it.

    class person {
      String firstName
      String lastName
    }
    context.theGuy = new person(firstName: "John", lastName: "Smith")

     

  • jkrier's avatar
    jkrier
    Regular Contributor
    This worked twice then I closed and reopened soapUI and it quit working and started to loop continuously without ever stopping.