sumolib.xml.xsd
1# -*- coding: utf-8 -*- 2# Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo 3# Copyright (C) 2014-2026 German Aerospace Center (DLR) and others. 4# This program and the accompanying materials are made available under the 5# terms of the Eclipse Public License 2.0 which is available at 6# https://www.eclipse.org/legal/epl-2.0/ 7# This Source Code may also be made available under the following Secondary 8# Licenses when the conditions for such availability set forth in the Eclipse 9# Public License 2.0 are satisfied: GNU General Public License, version 2 10# or later which is available at 11# https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html 12# SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later 13 14# @file xsd.py 15# @author Marek Heinrich 16# @author Michael Behrisch 17# @date 2014-01-20 18 19from __future__ import absolute_import 20 21import os 22from xml.dom import minidom 23 24 25class XmlAttribute: 26 27 def __init__(self, entity): 28 if hasattr(entity, "getAttribute"): 29 self.name = entity.getAttribute('name') 30 self.use = entity.getAttribute('use') 31 self.type = entity.getAttribute('type') 32 else: 33 self.name = entity 34 self.use = None 35 self.type = None 36 37 def __repr__(self): 38 return self.name 39 40 41class XmlElement: 42 43 def __init__(self, entity): 44 self.name = entity.getAttribute('name') 45 self.ref = entity.getAttribute('ref') 46 self.type = entity.getAttribute('type') 47 self.attributes = [] 48 self.children = [] 49 self.resolved = False 50 51 def __repr__(self): 52 childList = [c.name for c in self.children] 53 return "name '%s' ref '%s' type '%s' attrs %s %s" % (self.name, self.ref, self.type, self.attributes, childList) 54 55 56class XsdStructure(): 57 58 def __init__(self, xsdFile): 59 with open(xsdFile) as xsdIn: 60 xmlDoc = minidom.parse(xsdIn) 61 self.root = None 62 self._namedElements = {} 63 self._namedTypes = {} 64 self._namedEnumerations = {} 65 for btEntity in xmlDoc.getElementsByTagName('xsd:include'): 66 path = btEntity.getAttribute('schemaLocation') 67 fullPath = os.path.join(os.path.dirname(xsdFile), path) 68 subStruc = XsdStructure(fullPath) 69 self._namedElements.update(subStruc._namedElements) 70 self._namedTypes.update(subStruc._namedTypes) 71 for btEntity in xmlDoc.getElementsByTagName('xsd:element'): 72 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 73 el = self.getElementStructure(btEntity, True) 74 self._namedElements[el.name] = el 75 if self.root is None: 76 self.root = el 77 for btEntity in xmlDoc.getElementsByTagName('xsd:complexType'): 78 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 79 el = self.getElementStructure(btEntity) 80 self._namedTypes[el.name] = el 81 for btEntity in xmlDoc.getElementsByTagName('xsd:simpleType'): 82 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 83 enum = [e.getAttribute( 84 'value') for e in btEntity.getElementsByTagName('xsd:enumeration')] 85 if enum: 86 self._namedEnumerations[ 87 btEntity.getAttribute('name')] = enum 88 self.resolveRefs() 89# pp = pprint.PrettyPrinter(indent=4) 90# pp.pprint(self._namedElements) 91# pp.pprint(self._namedTypes) 92# pp.pprint(self._namedEnumerations) 93 94 def getEnumeration(self, name): 95 return self._namedEnumerations.get(name, None) 96 97 def getEnumerationByAttr(self, ele, attr): 98 if ele in self._namedElements: 99 for a in self._namedElements[ele].attributes: 100 if a.name == attr: 101 return self._namedEnumerations.get(a.type, None) 102 return None 103 104 def getElementStructure(self, entity, checkNestedType=False): 105 eleObj = XmlElement(entity) 106 if checkNestedType: 107 nestedTypes = entity.getElementsByTagName('xsd:complexType') 108 if nestedTypes: 109 entity = nestedTypes[0] # skip xsd:complex-tag 110 for ext in entity.getElementsByTagName('xsd:extension'): 111 if ext.parentNode.parentNode == entity: 112 eleObj.type = ext.getAttribute('base') 113 entity = ext 114 break 115 for aa in entity.childNodes: 116 if aa.nodeName == 'xsd:attribute': 117 eleObj.attributes.append(XmlAttribute(aa)) 118 elif aa.nodeName == 'xsd:sequence' or aa.nodeName == 'xsd:choice': 119 for aae in aa.getElementsByTagName('xsd:element'): 120 eleObj.children.append(XmlElement(aae)) 121 return eleObj 122 123 def resolveRefs(self): 124 for ele in self._namedTypes.values(): 125 if ele.type and ele.type in self._namedTypes and not ele.resolved: 126 t = self._namedTypes[ele.type] 127 ele.attributes += t.attributes 128 ele.children += t.children 129 ele.resolved = True 130 for ele in self._namedElements.values(): 131 if ele.type and ele.type in self._namedTypes and not ele.resolved: 132 t = self._namedTypes[ele.type] 133 ele.attributes += t.attributes 134 ele.children += t.children 135 ele.resolved = True 136 for ele in self._namedElements.values(): 137 newChildren = [] 138 for child in ele.children: 139 if child.ref: 140 newChildren.append(self._namedElements[child.ref]) 141 else: 142 newChildren.append(self._namedElements[child.name]) 143 ele.children = newChildren
class
XmlAttribute:
26class XmlAttribute: 27 28 def __init__(self, entity): 29 if hasattr(entity, "getAttribute"): 30 self.name = entity.getAttribute('name') 31 self.use = entity.getAttribute('use') 32 self.type = entity.getAttribute('type') 33 else: 34 self.name = entity 35 self.use = None 36 self.type = None 37 38 def __repr__(self): 39 return self.name
class
XmlElement:
42class XmlElement: 43 44 def __init__(self, entity): 45 self.name = entity.getAttribute('name') 46 self.ref = entity.getAttribute('ref') 47 self.type = entity.getAttribute('type') 48 self.attributes = [] 49 self.children = [] 50 self.resolved = False 51 52 def __repr__(self): 53 childList = [c.name for c in self.children] 54 return "name '%s' ref '%s' type '%s' attrs %s %s" % (self.name, self.ref, self.type, self.attributes, childList)
class
XsdStructure:
57class XsdStructure(): 58 59 def __init__(self, xsdFile): 60 with open(xsdFile) as xsdIn: 61 xmlDoc = minidom.parse(xsdIn) 62 self.root = None 63 self._namedElements = {} 64 self._namedTypes = {} 65 self._namedEnumerations = {} 66 for btEntity in xmlDoc.getElementsByTagName('xsd:include'): 67 path = btEntity.getAttribute('schemaLocation') 68 fullPath = os.path.join(os.path.dirname(xsdFile), path) 69 subStruc = XsdStructure(fullPath) 70 self._namedElements.update(subStruc._namedElements) 71 self._namedTypes.update(subStruc._namedTypes) 72 for btEntity in xmlDoc.getElementsByTagName('xsd:element'): 73 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 74 el = self.getElementStructure(btEntity, True) 75 self._namedElements[el.name] = el 76 if self.root is None: 77 self.root = el 78 for btEntity in xmlDoc.getElementsByTagName('xsd:complexType'): 79 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 80 el = self.getElementStructure(btEntity) 81 self._namedTypes[el.name] = el 82 for btEntity in xmlDoc.getElementsByTagName('xsd:simpleType'): 83 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 84 enum = [e.getAttribute( 85 'value') for e in btEntity.getElementsByTagName('xsd:enumeration')] 86 if enum: 87 self._namedEnumerations[ 88 btEntity.getAttribute('name')] = enum 89 self.resolveRefs() 90# pp = pprint.PrettyPrinter(indent=4) 91# pp.pprint(self._namedElements) 92# pp.pprint(self._namedTypes) 93# pp.pprint(self._namedEnumerations) 94 95 def getEnumeration(self, name): 96 return self._namedEnumerations.get(name, None) 97 98 def getEnumerationByAttr(self, ele, attr): 99 if ele in self._namedElements: 100 for a in self._namedElements[ele].attributes: 101 if a.name == attr: 102 return self._namedEnumerations.get(a.type, None) 103 return None 104 105 def getElementStructure(self, entity, checkNestedType=False): 106 eleObj = XmlElement(entity) 107 if checkNestedType: 108 nestedTypes = entity.getElementsByTagName('xsd:complexType') 109 if nestedTypes: 110 entity = nestedTypes[0] # skip xsd:complex-tag 111 for ext in entity.getElementsByTagName('xsd:extension'): 112 if ext.parentNode.parentNode == entity: 113 eleObj.type = ext.getAttribute('base') 114 entity = ext 115 break 116 for aa in entity.childNodes: 117 if aa.nodeName == 'xsd:attribute': 118 eleObj.attributes.append(XmlAttribute(aa)) 119 elif aa.nodeName == 'xsd:sequence' or aa.nodeName == 'xsd:choice': 120 for aae in aa.getElementsByTagName('xsd:element'): 121 eleObj.children.append(XmlElement(aae)) 122 return eleObj 123 124 def resolveRefs(self): 125 for ele in self._namedTypes.values(): 126 if ele.type and ele.type in self._namedTypes and not ele.resolved: 127 t = self._namedTypes[ele.type] 128 ele.attributes += t.attributes 129 ele.children += t.children 130 ele.resolved = True 131 for ele in self._namedElements.values(): 132 if ele.type and ele.type in self._namedTypes and not ele.resolved: 133 t = self._namedTypes[ele.type] 134 ele.attributes += t.attributes 135 ele.children += t.children 136 ele.resolved = True 137 for ele in self._namedElements.values(): 138 newChildren = [] 139 for child in ele.children: 140 if child.ref: 141 newChildren.append(self._namedElements[child.ref]) 142 else: 143 newChildren.append(self._namedElements[child.name]) 144 ele.children = newChildren
XsdStructure(xsdFile)
59 def __init__(self, xsdFile): 60 with open(xsdFile) as xsdIn: 61 xmlDoc = minidom.parse(xsdIn) 62 self.root = None 63 self._namedElements = {} 64 self._namedTypes = {} 65 self._namedEnumerations = {} 66 for btEntity in xmlDoc.getElementsByTagName('xsd:include'): 67 path = btEntity.getAttribute('schemaLocation') 68 fullPath = os.path.join(os.path.dirname(xsdFile), path) 69 subStruc = XsdStructure(fullPath) 70 self._namedElements.update(subStruc._namedElements) 71 self._namedTypes.update(subStruc._namedTypes) 72 for btEntity in xmlDoc.getElementsByTagName('xsd:element'): 73 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 74 el = self.getElementStructure(btEntity, True) 75 self._namedElements[el.name] = el 76 if self.root is None: 77 self.root = el 78 for btEntity in xmlDoc.getElementsByTagName('xsd:complexType'): 79 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 80 el = self.getElementStructure(btEntity) 81 self._namedTypes[el.name] = el 82 for btEntity in xmlDoc.getElementsByTagName('xsd:simpleType'): 83 if btEntity.nodeType == 1 and btEntity.hasAttribute('name'): 84 enum = [e.getAttribute( 85 'value') for e in btEntity.getElementsByTagName('xsd:enumeration')] 86 if enum: 87 self._namedEnumerations[ 88 btEntity.getAttribute('name')] = enum 89 self.resolveRefs()
def
getElementStructure(self, entity, checkNestedType=False):
105 def getElementStructure(self, entity, checkNestedType=False): 106 eleObj = XmlElement(entity) 107 if checkNestedType: 108 nestedTypes = entity.getElementsByTagName('xsd:complexType') 109 if nestedTypes: 110 entity = nestedTypes[0] # skip xsd:complex-tag 111 for ext in entity.getElementsByTagName('xsd:extension'): 112 if ext.parentNode.parentNode == entity: 113 eleObj.type = ext.getAttribute('base') 114 entity = ext 115 break 116 for aa in entity.childNodes: 117 if aa.nodeName == 'xsd:attribute': 118 eleObj.attributes.append(XmlAttribute(aa)) 119 elif aa.nodeName == 'xsd:sequence' or aa.nodeName == 'xsd:choice': 120 for aae in aa.getElementsByTagName('xsd:element'): 121 eleObj.children.append(XmlElement(aae)) 122 return eleObj
def
resolveRefs(self):
124 def resolveRefs(self): 125 for ele in self._namedTypes.values(): 126 if ele.type and ele.type in self._namedTypes and not ele.resolved: 127 t = self._namedTypes[ele.type] 128 ele.attributes += t.attributes 129 ele.children += t.children 130 ele.resolved = True 131 for ele in self._namedElements.values(): 132 if ele.type and ele.type in self._namedTypes and not ele.resolved: 133 t = self._namedTypes[ele.type] 134 ele.attributes += t.attributes 135 ele.children += t.children 136 ele.resolved = True 137 for ele in self._namedElements.values(): 138 newChildren = [] 139 for child in ele.children: 140 if child.ref: 141 newChildren.append(self._namedElements[child.ref]) 142 else: 143 newChildren.append(self._namedElements[child.name]) 144 ele.children = newChildren