I need to traverse the XML tree to add sub element when the value is less than 5. For example, this XML can be modified into
<?xml version="1.0" encoding="UTF-8"?>
<A value="45">
    <B value="30">
        <C value="10"/>
        <C value ="20"/>
    </B>
    <B value="15">
        <C value = "5" />
        <C value = "10" />
    </B>
</A>
this XML.
<?xml version="1.0" encoding="UTF-8"?>
<A value="45">
    <B value="30">
        <C value="10"/>               
        <C value ="20"/>
    </B>
    <B value="15">
        <C value = "5"><D name="error"/></C>
        <C value = "10" />
    </B>
</A>
How can I do that with Python's ElementTree?
Creating XML Document using Python First, we import minidom for using xml. dom . Then we create the root element and append it to the XML. After that creating a child product of parent namely Geeks for Geeks.
The xml.etree.ElementTree module implements a simple and efficient API for parsing and creating XML data. Changed in version 3.3: This module will use a fast implementation whenever available.
You probably made a typo because in the example, an error element is appended as the child of an element whose value is 10, which is not less than 5. But I think this is the idea:
#!/usr/bin/env python
from xml.etree.ElementTree import fromstring, ElementTree, Element
def validate_node(elem):
    for child in elem.getchildren():
        validate_node(child)
        value = child.attrib.get('value', '')
        if not value.isdigit() or int(value) < 5:
            child.append(Element('D', {'name': 'error'}))
if __name__ == '__main__':
    import sys
    xml = sys.stdin.read() # read XML from standard input
    root = fromstring(xml) # parse into XML element tree
    validate_node(root)
    ElementTree(root).write(sys.stdout, encoding='utf-8')
            # write resulting XML to standard output
Given this input:
<?xml version="1.0" encoding="UTF-8"?>
<A value="45">
    <B value="30">
        <C value="1"/>
        <C value="20"/>
    </B>
    <B value="15">
        <C value="5" />
        <C value="10" />
        <C value="foo" />
    </B>
</A>
This is is the output:
<A value="45">
    <B value="30">
        <C value="1"><D name="error" /></C>
        <C value="20" />
    </B>
    <B value="15">
        <C value="5" />
        <C value="10" />
        <C value="foo"><D name="error" /></C>
    </B>
</A>
                        ElementTree's iter (or getiterator for Python <2.7) willl recursively return all the nodes in a tree, then just test for your condition and create the SubElement:
from xml.etree import ElementTree as ET
tree = ET.parse(input)
for e in tree.getiterator():
    if int(e.get('value')) < 5:
        ET.SubElement(e,'D',dict(name='error'))
                        If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With