Geeta Geeta - 3 months ago 12
Groovy Question

how to fail groovy script via assert, if xml node is not present in Switch statement

This is my script,

import groovy.xml.*

def xml = '''<ROOT>
<Profile>12</Profile>
<Rate>3072</Rate>
<AudioRate>0</AudioRate>
<GPS>15</GPS>
</ROOT>'''

def Xmlnodes = new XmlParser().parseText(xml)

Xmlnodes.each { setting ->

switch (setting.name()) {
case 'Profile': break;
case 'Rate': break;
case 'GPS': break;
default: log.info "Unknown Unit Config Element: " + setting.name()
}
}


How can I fail this script as AudioRate node is not present in switch statement

Answer

If you want to validate that your XML contains at least one <AudioRate/> element, it's not necessary to do so inside the switch.

You can add an assert to check if at least one <AudioRate/> element exists in your XML as follows:

assert Xmlnodes.'**'.findAll { it.name() == 'AudioRate' }.size() > 0

If you've a list of required node names you can use the follow code to make fail your test if some of these names are not present in the XML:

// required node names
['Profile','Rate','AudioRate','GPS'].each { nodeName ->
    assert Xmlnodes.'**'.findAll { it.name() == nodeName }.size() > 0
}

UPDATE:

I think that I misunderstood your requeriment, and instead of check that your XML has at least all required elements you are looking for a check to validate that XML only contains allowed elements. If this is the case you can do it using your switch by simply adding an assert false in your default.

Xmlnodes.each { setting ->
  switch (setting.name()) {
    case 'Profile': break;
    case 'Rate': break;
    case 'GPS': break;
    default: 
         log.info "Unknown Unit Config Element: " + setting.name()
         assert false
  }   
}

Or in a more Groovy way, checking that all XML node names are in allowed list:

assert ['Profile','Rate','GPS'].containsAll(Xmlnodes*.name())‚Äč

UPDATE 2:

Based on your comments from the chat, if you want to check first if all child node names of <Screen> (in case that at least on exists) are in allowed list and then perform the check for allowed names in the <ROOT> node, you can do something like:

def xml = '''<ROOT> 
    <Profile>12</Profile> 
    <Rate>3072</Rate> 
    <AudioRate>0</AudioRate> 
    <GPS>15</GPS> 
    <Screen> 
        <Video>12</Video> 
        <Rate>600</Rate> 
        <Camera>1</Camera> 
    </Screen> 
    <Screen> 
        <Devices> 
            <audioDevice>1</audioDevice> 
        </Devices> 
    </Screen>
</ROOT>'''

def Xmlnodes = new XmlParser().parseText(xml)

// <Screen> nodes exists...
if(Xmlnodes.Screen){
    // [Video, Rate, Camera, Devices] --> [Video,Rate,Camera] are from first <Screen> [Devices] are from the second <Screen>
    println Xmlnodes.Screen*.collect { it.name() }.sum() 

    // get all childnode names for all the possible <Screen> elements in one list and
    // check that all names are allowed
    assert ['Video', 'Rate', 'Camera', 'Devices'].containsAll(Xmlnodes.Screen*.collect { it.name() }.sum() )
}

// check that only allowed names are in xml
assert ['Profile','Rate','GPS','AudioRate','Screen'].containsAll(Xmlnodes*.name())

UPDATE 3:

Since in your last comment, you told that you want to know also the name of the unknown tags on the XML, then you can perform a - operations from your predefined list of node names, this way the rest are the unknown elements; this is my last attempt:

def Xmlnodes = new XmlParser().parseText(xml)

def screenUnknown = []

// <Screen> nodes exists...
if(Xmlnodes.Screen){
    // get all unknown elements
    screenUnknown = Xmlnodes.Screen*.collect { it.name() }.sum() - ['Video', 'Rate', 'Camera', 'Devices']
}

// get all unknown nodes in root
def rootUnknown = Xmlnodes*.name() -  ['Profile','Rate','GPS','AudioRate','Screen']

println "unknown in <Root>: ${rootUnknown}"
println "unknown in <Screen>: ${screenUnknown}"

// optionally you can make an assert to check
// that there aren't unknown elements
assert rootUnknown.size() == 0, 'THE ARE UNKNOWN ELEMENTS IN <ROOT>'
assert screenUnknown.size()  == 0,  'THE ARE UNKNOWN ELEMENTS IN <SCREEN>'

Hope it helps,

Comments