Last active
November 23, 2015 14:42
-
-
Save Deiru2k/a0e436dd8f88a0da08c1 to your computer and use it in GitHub Desktop.
Dict To Xml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from xml.etree import ElementTree as et | |
from xml.dom import minidom | |
""" | |
Convert Python dict to XML using a special set of rules | |
Function build_xml takes a specialy formatted dict and returns xml.etree.ElementTree Element. | |
1) There can be only one Root Element, it must be at a top-level of a dictionary and it should be the only element at | |
top-level | |
2) Keys are element names, key values should be dicts with element params. | |
3) If there should be more than one elements with the same name, key value could be a list of dicts with params. | |
4) If element should have children, they must be defined within "children" param | |
5) Attributes should be a dict containing a list of attributes of element, where key is attribute name and it's value | |
is attribute's value | |
Example of a dict that complies to such rules: | |
my_xml = { | |
"root": { | |
"children": { | |
"child": { | |
"attributes": {"myAttr1": "1", "myAttr2": "dogeshibe"}, | |
"content": "Wow, such content, very within element, much tags", | |
"children": { | |
"doge": [ | |
{"content": "Doge 1"}, | |
{"content": "Doge 2"} | |
] | |
} | |
} | |
} | |
} | |
} | |
This should convert into: | |
<root> | |
<child myAttr1="1" myAttr2="dogeshibe"> | |
Wow, such content, very within element, much tags | |
<doge>Doge 1</doge> | |
<doge>Doge 2</doge> | |
</child> | |
</root> | |
You can try to construct your dict and convert to XML | |
You can use prettify function to make a pretty, tab-formatted string from your Element. | |
@Misaka42, 2015 | |
Do whatever the fuck you want. | |
""" | |
def build_xml(d): | |
""" | |
Builds XML from dict | |
""" | |
root_key = d.keys()[0] | |
root = d[root_key] | |
root_element = et.Element(root_key) | |
if 'content' in root: root_element.text = root['content'] | |
if 'attributes' in root: root_element.attrib = root['attributes'] | |
result = process_tree(root['children'], root_element) | |
return result | |
def process_tree(tree, root_element): | |
def process_node(key, node): | |
element = et.Element(key) | |
if 'content' in node: | |
element.text = node['content'] | |
if 'attributes' in node: element.attrib = node['attributes'] | |
if 'children' in node: | |
element = process_tree(node['children'], element) | |
root_element.append(element) | |
for key in tree: | |
node = tree[key] | |
if isinstance(node, dict): | |
process_node(key, node) | |
elif isinstance(node, list): | |
for n in node: process_node(key, n) | |
return root_element | |
def prettify(elem): | |
"""Return a pretty-printed XML string for the Element. | |
""" | |
rough_string = et.tostring(elem, 'utf-8') | |
reparsed = minidom.parseString(rough_string) | |
return reparsed.toprettyxml(indent=" " * 2) | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment