From 7cff26f60b7ff49314e7f96f483624a0e48641be Mon Sep 17 00:00:00 2001
From: Sapan Bhatia <sapanb@cs.princeton.edu>
Date: Wed, 8 Jul 2009 19:37:30 +0000
Subject: [PATCH] Generic XML-->nested dict parser

---
 sfa/util/rspec.py | 38 +++++++++++++++++++++++++++++++++++++-
 1 file changed, 37 insertions(+), 1 deletion(-)

diff --git a/sfa/util/rspec.py b/sfa/util/rspec.py
index 6008b8d2..1cd7edc6 100644
--- a/sfa/util/rspec.py
+++ b/sfa/util/rspec.py
@@ -70,6 +70,42 @@ class Rspec:
         return node
   
  
+    def appendToDictOrCreate(self, dict, key, value):
+        if (dict.has_key(key)):
+            dict[key].append(value)
+        else:
+            dict[key]=[value]
+        return dict
+
+    def toGenDict(self, nodeDom=None, parentdict={}, siblingdict={}, parent=None):
+        """
+        convert an XML to a nested dict:
+          * Non-terminal nodes (elements with string children and attributes) are simple dictionaries
+          * Terminal nodes (the rest) are nested dictionaries
+        """
+
+        if (not nodeDom):
+            nodeDom=self.rootNode
+
+        curNodeName = nodeDom.localName
+
+        if (nodeDom.nodeValue):
+            siblingdict = self.appendToDictOrCreate(siblingdict, parent, nodeDom.nodeValue)
+        elif (nodeDom.hasChildNodes()):
+            for child in nodeDom.childNodes:
+                 siblingdict = self.toGenDict(child, None, siblingdict,curNodeName)
+
+            for attribute in nodeDom.attributes.keys():
+                parentdict = self.appendToDictOrCreate(parentdict, curNodeName, nodeDom.getAttribute(attribute))
+
+        if (parentdict is not None):
+            parentdict = self.appendToDictOrCreate(parentdict, curNodeName, siblingdict)
+            return parentdict
+        else:
+            return siblingdict
+
+
+
     def toDict(self, nodeDom = None):
         """
         convert this rspec to a dict and return it.
@@ -132,7 +168,7 @@ class Rspec:
         """
         read an xml string and store it as a dom object.
         """
-        xml = xml.replace('\n', '').replace('\t', '').strip()
+        xml = xml.replace('\n', '').replace('\t', '').replace(' ', '').strip()
         dom = minidom.parseString(xml)
         self.rootNode = dom.childNodes[0]
 
-- 
2.47.0