0

I have config.json file i need to generate xml file based on config file

my config file looks like.

{
"Elements": [
        {
            "Element type": "root",
            "Element name": "root_element"
        },
        {
            "Element type": "sub_element",
            "Parent element": "root_element",
            "Element name": "AAA"
        },
        {
            "Element type": "sub_element",
            "Parent element": "AAA",
            "Element name": "BBB"
        },
        {
            "Element type": "sub_element",
            "Parent element": "BBB",
            "Element name": "CCC"
        },
        {
            "Element type": "sub_element",
            "Parent element": "CCC",
            "Element name": "DDD"
        }
    ]
}

I need to write python a code to generate nested xml based above file

I tried but i am not getting exact output

def generate():
    config_path = os.path.join(os.getcwd(), "config", "xml_config.json")
    data = json.load(open(config_path))
    root = None
    for i in data['Elements']:
        if i['Element type'] == 'root':
            root = et.Element(i['Element name'])
        if i['Element type'] == 'sub_element':
            path = root.find(i['Parent element'])
            if path is None:
                et.SubElement(root, i['Element name'])
            else:
                et.SubElement(root.find(i['Parent element']), i['Element name'])
    print(et.tostring(root, encoding='unicode', method='xml'))

My current output looks like:

<root_element>
<AAA>
    <BBB />
</AAA>
<CCC />
<DDD />
</root_element>

But my expected output is:

<root_element>
   <AAA>
       <BBB>
           <CCC>
               <DDD />
           <CCC />
       </BBB>
   </AAA>
</root_element>
dp808139
  • 122
  • 2
  • 12
  • The hierarchy of your JSON file isn't really matching the hierarchy you want to create in your XML. If you have control over the JSON format too, it would make more sense to have them match the same structure – Emmanuel Murairi May 01 '23 at 08:44

2 Answers2

0

I got the solution we need to maintain one dictionary.

def generate():
    config_path = os.path.join(os.getcwd(), "config.json")
    data = json.load(open(config_path))
    root = None
    elements_map = {}
    for i in data['Elements']:
        element_type = i['Element type']
        element_name = i['Element name']
        parent_element_name = i.get('Parent element')
        if element_type == 'root':
            root = et.Element(element_name)
            elements_map[element_name] = root
        elif element_type == 'sub_element':
            parent_element = elements_map.get(parent_element_name)
            if parent_element is None:
                raise ValueError(f"Parent element '{parent_element_name}' not found.")
            element = et.SubElement(parent_element, element_name)
            elements_map[element_name] = element
    xml_string = et.tostring(root, encoding='unicode', method='xml')
    print(xml_string)
dp808139
  • 122
  • 2
  • 12
0

I would do it this way :

import json
import xml.etree.ElementTree as ET

obj = json.load(open("config.json"))

elements = {}
elements[root.tag] = ET.Element(obj["Elements"][0]["Element name"])

for el in obj["Elements"][1:]:
    parent = elements[el["Parent element"]]
    elements[el["Element name"]] = ET.SubElement(parent, el["Element name"])

ET.ElementTree(root).write("out.xml", encoding="utf-8", xml_declaration=True)

Output (out.xml) :

<?xml version="1.0" encoding="UTF-8"?>
<root_element>
   <AAA>
      <BBB>
         <CCC>
            <DDD />
         </CCC>
      </BBB>
   </AAA>
</root_element>
Timeless
  • 22,580
  • 4
  • 12
  • 30