You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

2960 lines
101 KiB

  1. # Copyright (c) 2003, The Regents of the University of California,
  2. # through Lawrence Berkeley National Laboratory (subject to receipt of
  3. # any required approvals from the U.S. Dept. of Energy). All rights
  4. # reserved.
  5. #
  6. # Copyright (c) 2001 Zope Corporation and Contributors. All Rights Reserved.
  7. #
  8. # This software is subject to the provisions of the Zope Public License,
  9. # Version 2.0 (ZPL). A copy of the ZPL should accompany this distribution.
  10. # THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
  11. # WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
  12. # WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
  13. # FOR A PARTICULAR PURPOSE.
  14. ident = "$Id$"
  15. import types, weakref, sys
  16. from threading import RLock
  17. from Namespaces import XMLNS
  18. from Utility import DOM, DOMException, Collection, SplitQName, basejoin
  19. from StringIO import StringIO
  20. #
  21. # Collections in XMLSchema class
  22. #
  23. TYPES = 'types'
  24. ATTRIBUTE_GROUPS = 'attr_groups'
  25. ATTRIBUTES = 'attr_decl'
  26. ELEMENTS = 'elements'
  27. MODEL_GROUPS = 'model_groups'
  28. def GetSchema(component):
  29. """convience function for finding the parent XMLSchema instance.
  30. """
  31. parent = component
  32. while not isinstance(parent, XMLSchema):
  33. parent = parent._parent()
  34. return parent
  35. class SchemaReader:
  36. """A SchemaReader creates XMLSchema objects from urls and xml data.
  37. """
  38. def __init__(self, domReader=None, base_url=None):
  39. """domReader -- class must implement DOMAdapterInterface
  40. base_url -- base url string
  41. """
  42. self.__base_url = base_url
  43. self.__readerClass = domReader
  44. if not self.__readerClass:
  45. self.__readerClass = DOMAdapter
  46. self._includes = {}
  47. self._imports = {}
  48. def __setImports(self, schema):
  49. """Add dictionary of imports to schema instance.
  50. schema -- XMLSchema instance
  51. """
  52. for ns,val in schema.imports.items():
  53. if self._imports.has_key(ns):
  54. schema.addImportSchema(self._imports[ns])
  55. def __setIncludes(self, schema):
  56. """Add dictionary of includes to schema instance.
  57. schema -- XMLSchema instance
  58. """
  59. for schemaLocation, val in schema.includes.items():
  60. if self._includes.has_key(schemaLocation):
  61. schema.addIncludeSchema(self._imports[schemaLocation])
  62. def addSchemaByLocation(self, location, schema):
  63. """provide reader with schema document for a location.
  64. """
  65. self._includes[location] = schema
  66. def addSchemaByNamespace(self, schema):
  67. """provide reader with schema document for a targetNamespace.
  68. """
  69. self._imports[schema.targetNamespace] = schema
  70. def loadFromNode(self, parent, element):
  71. """element -- DOM node or document
  72. parent -- WSDLAdapter instance
  73. """
  74. reader = self.__readerClass(element)
  75. schema = XMLSchema(parent)
  76. #HACK to keep a reference
  77. schema.wsdl = parent
  78. schema.setBaseUrl(self.__base_url)
  79. schema.load(reader)
  80. return schema
  81. def loadFromStream(self, file, url=None):
  82. """Return an XMLSchema instance loaded from a file object.
  83. file -- file object
  84. url -- base location for resolving imports/includes.
  85. """
  86. reader = self.__readerClass()
  87. reader.loadDocument(file)
  88. schema = XMLSchema()
  89. if url is not None:
  90. schema.setBaseUrl(url)
  91. schema.load(reader)
  92. self.__setIncludes(schema)
  93. self.__setImports(schema)
  94. return schema
  95. def loadFromString(self, data):
  96. """Return an XMLSchema instance loaded from an XML string.
  97. data -- XML string
  98. """
  99. return self.loadFromStream(StringIO(data))
  100. def loadFromURL(self, url):
  101. """Return an XMLSchema instance loaded from the given url.
  102. url -- URL to dereference
  103. """
  104. reader = self.__readerClass()
  105. if self.__base_url:
  106. url = basejoin(self.__base_url,url)
  107. reader.loadFromURL(url)
  108. schema = XMLSchema()
  109. schema.setBaseUrl(url)
  110. schema.load(reader)
  111. self.__setIncludes(schema)
  112. self.__setImports(schema)
  113. return schema
  114. def loadFromFile(self, filename):
  115. """Return an XMLSchema instance loaded from the given file.
  116. filename -- name of file to open
  117. """
  118. if self.__base_url:
  119. filename = basejoin(self.__base_url,filename)
  120. file = open(filename, 'rb')
  121. try:
  122. schema = self.loadFromStream(file, filename)
  123. finally:
  124. file.close()
  125. return schema
  126. class SchemaError(Exception):
  127. pass
  128. ###########################
  129. # DOM Utility Adapters
  130. ##########################
  131. class DOMAdapterInterface:
  132. def hasattr(self, attr, ns=None):
  133. """return true if node has attribute
  134. attr -- attribute to check for
  135. ns -- namespace of attribute, by default None
  136. """
  137. raise NotImplementedError, 'adapter method not implemented'
  138. def getContentList(self, *contents):
  139. """returns an ordered list of child nodes
  140. *contents -- list of node names to return
  141. """
  142. raise NotImplementedError, 'adapter method not implemented'
  143. def setAttributeDictionary(self, attributes):
  144. """set attribute dictionary
  145. """
  146. raise NotImplementedError, 'adapter method not implemented'
  147. def getAttributeDictionary(self):
  148. """returns a dict of node's attributes
  149. """
  150. raise NotImplementedError, 'adapter method not implemented'
  151. def getNamespace(self, prefix):
  152. """returns namespace referenced by prefix.
  153. """
  154. raise NotImplementedError, 'adapter method not implemented'
  155. def getTagName(self):
  156. """returns tagName of node
  157. """
  158. raise NotImplementedError, 'adapter method not implemented'
  159. def getParentNode(self):
  160. """returns parent element in DOMAdapter or None
  161. """
  162. raise NotImplementedError, 'adapter method not implemented'
  163. def loadDocument(self, file):
  164. """load a Document from a file object
  165. file --
  166. """
  167. raise NotImplementedError, 'adapter method not implemented'
  168. def loadFromURL(self, url):
  169. """load a Document from an url
  170. url -- URL to dereference
  171. """
  172. raise NotImplementedError, 'adapter method not implemented'
  173. class DOMAdapter(DOMAdapterInterface):
  174. """Adapter for ZSI.Utility.DOM
  175. """
  176. def __init__(self, node=None):
  177. """Reset all instance variables.
  178. element -- DOM document, node, or None
  179. """
  180. if hasattr(node, 'documentElement'):
  181. self.__node = node.documentElement
  182. else:
  183. self.__node = node
  184. self.__attributes = None
  185. def getNode(self):
  186. return self.__node
  187. def hasattr(self, attr, ns=None):
  188. """attr -- attribute
  189. ns -- optional namespace, None means unprefixed attribute.
  190. """
  191. if not self.__attributes:
  192. self.setAttributeDictionary()
  193. if ns:
  194. return self.__attributes.get(ns,{}).has_key(attr)
  195. return self.__attributes.has_key(attr)
  196. def getContentList(self, *contents):
  197. nodes = []
  198. ELEMENT_NODE = self.__node.ELEMENT_NODE
  199. for child in DOM.getElements(self.__node, None):
  200. if child.nodeType == ELEMENT_NODE and\
  201. SplitQName(child.tagName)[1] in contents:
  202. nodes.append(child)
  203. return map(self.__class__, nodes)
  204. def setAttributeDictionary(self):
  205. self.__attributes = {}
  206. for v in self.__node._attrs.values():
  207. self.__attributes[v.nodeName] = v.nodeValue
  208. def getAttributeDictionary(self):
  209. if not self.__attributes:
  210. self.setAttributeDictionary()
  211. return self.__attributes
  212. def getTagName(self):
  213. return self.__node.tagName
  214. def getParentNode(self):
  215. if self.__node.parentNode.nodeType == self.__node.ELEMENT_NODE:
  216. return DOMAdapter(self.__node.parentNode)
  217. return None
  218. def getNamespace(self, prefix):
  219. """prefix -- deference namespace prefix in node's context.
  220. Ascends parent nodes until found.
  221. """
  222. namespace = None
  223. if prefix == 'xmlns':
  224. namespace = DOM.findDefaultNS(prefix, self.__node)
  225. else:
  226. try:
  227. namespace = DOM.findNamespaceURI(prefix, self.__node)
  228. except DOMException, ex:
  229. if prefix != 'xml':
  230. raise SchemaError, '%s namespace not declared for %s'\
  231. %(prefix, self.__node._get_tagName())
  232. namespace = XMLNS.XML
  233. return namespace
  234. def loadDocument(self, file):
  235. self.__node = DOM.loadDocument(file)
  236. if hasattr(self.__node, 'documentElement'):
  237. self.__node = self.__node.documentElement
  238. def loadFromURL(self, url):
  239. self.__node = DOM.loadFromURL(url)
  240. if hasattr(self.__node, 'documentElement'):
  241. self.__node = self.__node.documentElement
  242. class XMLBase:
  243. """ These class variables are for string indentation.
  244. """
  245. tag = None
  246. __indent = 0
  247. __rlock = RLock()
  248. def __str__(self):
  249. XMLBase.__rlock.acquire()
  250. XMLBase.__indent += 1
  251. tmp = "<" + str(self.__class__) + '>\n'
  252. for k,v in self.__dict__.items():
  253. tmp += "%s* %s = %s\n" %(XMLBase.__indent*' ', k, v)
  254. XMLBase.__indent -= 1
  255. XMLBase.__rlock.release()
  256. return tmp
  257. """Marker Interface: can determine something about an instances properties by using
  258. the provided convenience functions.
  259. """
  260. class DefinitionMarker:
  261. """marker for definitions
  262. """
  263. pass
  264. class DeclarationMarker:
  265. """marker for declarations
  266. """
  267. pass
  268. class AttributeMarker:
  269. """marker for attributes
  270. """
  271. pass
  272. class AttributeGroupMarker:
  273. """marker for attribute groups
  274. """
  275. pass
  276. class WildCardMarker:
  277. """marker for wildcards
  278. """
  279. pass
  280. class ElementMarker:
  281. """marker for wildcards
  282. """
  283. pass
  284. class ReferenceMarker:
  285. """marker for references
  286. """
  287. pass
  288. class ModelGroupMarker:
  289. """marker for model groups
  290. """
  291. pass
  292. class AllMarker(ModelGroupMarker):
  293. """marker for all model group
  294. """
  295. pass
  296. class ChoiceMarker(ModelGroupMarker):
  297. """marker for choice model group
  298. """
  299. pass
  300. class SequenceMarker(ModelGroupMarker):
  301. """marker for sequence model group
  302. """
  303. pass
  304. class ExtensionMarker:
  305. """marker for extensions
  306. """
  307. pass
  308. class RestrictionMarker:
  309. """marker for restrictions
  310. """
  311. facets = ['enumeration', 'length', 'maxExclusive', 'maxInclusive',\
  312. 'maxLength', 'minExclusive', 'minInclusive', 'minLength',\
  313. 'pattern', 'fractionDigits', 'totalDigits', 'whiteSpace']
  314. class SimpleMarker:
  315. """marker for simple type information
  316. """
  317. pass
  318. class ListMarker:
  319. """marker for simple type list
  320. """
  321. pass
  322. class UnionMarker:
  323. """marker for simple type Union
  324. """
  325. pass
  326. class ComplexMarker:
  327. """marker for complex type information
  328. """
  329. pass
  330. class LocalMarker:
  331. """marker for complex type information
  332. """
  333. pass
  334. class MarkerInterface:
  335. def isDefinition(self):
  336. return isinstance(self, DefinitionMarker)
  337. def isDeclaration(self):
  338. return isinstance(self, DeclarationMarker)
  339. def isAttribute(self):
  340. return isinstance(self, AttributeMarker)
  341. def isAttributeGroup(self):
  342. return isinstance(self, AttributeGroupMarker)
  343. def isElement(self):
  344. return isinstance(self, ElementMarker)
  345. def isReference(self):
  346. return isinstance(self, ReferenceMarker)
  347. def isWildCard(self):
  348. return isinstance(self, WildCardMarker)
  349. def isModelGroup(self):
  350. return isinstance(self, ModelGroupMarker)
  351. def isAll(self):
  352. return isinstance(self, AllMarker)
  353. def isChoice(self):
  354. return isinstance(self, ChoiceMarker)
  355. def isSequence(self):
  356. return isinstance(self, SequenceMarker)
  357. def isExtension(self):
  358. return isinstance(self, ExtensionMarker)
  359. def isRestriction(self):
  360. return isinstance(self, RestrictionMarker)
  361. def isSimple(self):
  362. return isinstance(self, SimpleMarker)
  363. def isComplex(self):
  364. return isinstance(self, ComplexMarker)
  365. def isLocal(self):
  366. return isinstance(self, LocalMarker)
  367. def isList(self):
  368. return isinstance(self, ListMarker)
  369. def isUnion(self):
  370. return isinstance(self, UnionMarker)
  371. ##########################################################
  372. # Schema Components
  373. #########################################################
  374. class XMLSchemaComponent(XMLBase, MarkerInterface):
  375. """
  376. class variables:
  377. required -- list of required attributes
  378. attributes -- dict of default attribute values, including None.
  379. Value can be a function for runtime dependencies.
  380. contents -- dict of namespace keyed content lists.
  381. 'xsd' content of xsd namespace.
  382. xmlns_key -- key for declared xmlns namespace.
  383. xmlns -- xmlns is special prefix for namespace dictionary
  384. xml -- special xml prefix for xml namespace.
  385. """
  386. required = []
  387. attributes = {}
  388. contents = {}
  389. xmlns_key = ''
  390. xmlns = 'xmlns'
  391. xml = 'xml'
  392. def __init__(self, parent=None):
  393. """parent -- parent instance
  394. instance variables:
  395. attributes -- dictionary of node's attributes
  396. """
  397. self.attributes = None
  398. self._parent = parent
  399. if self._parent:
  400. self._parent = weakref.ref(parent)
  401. if not self.__class__ == XMLSchemaComponent\
  402. and not (type(self.__class__.required) == type(XMLSchemaComponent.required)\
  403. and type(self.__class__.attributes) == type(XMLSchemaComponent.attributes)\
  404. and type(self.__class__.contents) == type(XMLSchemaComponent.contents)):
  405. raise RuntimeError, 'Bad type for a class variable in %s' %self.__class__
  406. def getItemTrace(self):
  407. """Returns a node trace up to the <schema> item.
  408. """
  409. item, path, name, ref = self, [], 'name', 'ref'
  410. while not isinstance(item,XMLSchema) and not isinstance(item,WSDLToolsAdapter):
  411. attr = item.getAttribute(name)
  412. if attr is None:
  413. attr = item.getAttribute(ref)
  414. if attr is None: path.append('<%s>' %(item.tag))
  415. else: path.append('<%s ref="%s">' %(item.tag, attr))
  416. else:
  417. path.append('<%s name="%s">' %(item.tag,attr))
  418. item = item._parent()
  419. try:
  420. tns = item.getTargetNamespace()
  421. except:
  422. tns = ''
  423. path.append('<%s targetNamespace="%s">' %(item.tag, tns))
  424. path.reverse()
  425. return ''.join(path)
  426. def getTargetNamespace(self):
  427. """return targetNamespace
  428. """
  429. parent = self
  430. targetNamespace = 'targetNamespace'
  431. tns = self.attributes.get(targetNamespace)
  432. while not tns:
  433. parent = parent._parent()
  434. tns = parent.attributes.get(targetNamespace)
  435. return tns
  436. def getAttributeDeclaration(self, attribute):
  437. """attribute -- attribute with a QName value (eg. type).
  438. collection -- check types collection in parent Schema instance
  439. """
  440. return self.getQNameAttribute(ATTRIBUTES, attribute)
  441. def getAttributeGroup(self, attribute):
  442. """attribute -- attribute with a QName value (eg. type).
  443. collection -- check types collection in parent Schema instance
  444. """
  445. return self.getQNameAttribute(ATTRIBUTE_GROUPS, attribute)
  446. def getTypeDefinition(self, attribute):
  447. """attribute -- attribute with a QName value (eg. type).
  448. collection -- check types collection in parent Schema instance
  449. """
  450. return self.getQNameAttribute(TYPES, attribute)
  451. def getElementDeclaration(self, attribute):
  452. """attribute -- attribute with a QName value (eg. element).
  453. collection -- check elements collection in parent Schema instance.
  454. """
  455. return self.getQNameAttribute(ELEMENTS, attribute)
  456. def getModelGroup(self, attribute):
  457. """attribute -- attribute with a QName value (eg. ref).
  458. collection -- check model_group collection in parent Schema instance.
  459. """
  460. return self.getQNameAttribute(MODEL_GROUPS, attribute)
  461. def getQNameAttribute(self, collection, attribute):
  462. """returns object instance representing QName --> (namespace,name),
  463. or if does not exist return None.
  464. attribute -- an information item attribute, with a QName value.
  465. collection -- collection in parent Schema instance to search.
  466. """
  467. obj = None
  468. #tdc = self.attributes.get(attribute)
  469. tdc = self.getAttributeQName(attribute)
  470. if tdc:
  471. obj = self.getSchemaItem(collection, tdc.getTargetNamespace(), tdc.getName())
  472. return obj
  473. def getSchemaItem(self, collection, namespace, name):
  474. """returns object instance representing namespace, name,
  475. or if does not exist return None.
  476. namespace -- namespace item defined in.
  477. name -- name of item.
  478. collection -- collection in parent Schema instance to search.
  479. """
  480. obj = None
  481. parent = GetSchema(self)
  482. if parent.targetNamespace == namespace:
  483. try:
  484. obj = getattr(parent, collection)[name]
  485. except KeyError, ex:
  486. raise KeyError, "targetNamespace(%s) collection(%s) has no item(%s)"\
  487. %(namespace, collection, name)
  488. elif parent.imports.has_key(namespace):
  489. schema = parent.imports[namespace].getSchema()
  490. try:
  491. obj = getattr(schema, collection)[name]
  492. except KeyError, ex:
  493. raise KeyError, "targetNamespace(%s) collection(%s) has no item(%s)"\
  494. %(namespace, collection, name)
  495. return obj
  496. def getXMLNS(self, prefix=None):
  497. """deference prefix or by default xmlns, returns namespace.
  498. """
  499. if prefix == XMLSchemaComponent.xml:
  500. return XMLNS.XML
  501. parent = self
  502. ns = self.attributes[XMLSchemaComponent.xmlns].get(prefix or\
  503. XMLSchemaComponent.xmlns_key)
  504. while not ns:
  505. parent = parent._parent()
  506. ns = parent.attributes[XMLSchemaComponent.xmlns].get(prefix or\
  507. XMLSchemaComponent.xmlns_key)
  508. if not ns and isinstance(parent, WSDLToolsAdapter):
  509. if prefix is None:
  510. return ''
  511. raise SchemaError, 'unknown prefix %s' %prefix
  512. return ns
  513. def getAttribute(self, attribute):
  514. """return requested attribute value or None
  515. """
  516. if type(attribute) in (list, tuple):
  517. if len(attribute) != 2:
  518. raise LookupError, 'To access attributes must use name or (namespace,name)'
  519. return self.attributes.get(attribute[0]).get(attribute[1])
  520. return self.attributes.get(attribute)
  521. def getAttributeQName(self, attribute):
  522. """return requested attribute value as (namespace,name) or None
  523. """
  524. qname = self.getAttribute(attribute)
  525. if isinstance(qname, TypeDescriptionComponent) is True:
  526. return qname
  527. if qname is None:
  528. return None
  529. prefix,ncname = SplitQName(qname)
  530. namespace = self.getXMLNS(prefix)
  531. return TypeDescriptionComponent((namespace,ncname))
  532. def getAttributeName(self):
  533. """return attribute name or None
  534. """
  535. return self.getAttribute('name')
  536. def setAttributes(self, node):
  537. """Sets up attribute dictionary, checks for required attributes and
  538. sets default attribute values. attr is for default attribute values
  539. determined at runtime.
  540. structure of attributes dictionary
  541. ['xmlns'][xmlns_key] -- xmlns namespace
  542. ['xmlns'][prefix] -- declared namespace prefix
  543. [namespace][prefix] -- attributes declared in a namespace
  544. [attribute] -- attributes w/o prefix, default namespaces do
  545. not directly apply to attributes, ie Name can't collide
  546. with QName.
  547. """
  548. self.attributes = {XMLSchemaComponent.xmlns:{}}
  549. for k,v in node.getAttributeDictionary().items():
  550. prefix,value = SplitQName(k)
  551. if value == XMLSchemaComponent.xmlns:
  552. self.attributes[value][prefix or XMLSchemaComponent.xmlns_key] = v
  553. elif prefix:
  554. ns = node.getNamespace(prefix)
  555. if not ns:
  556. raise SchemaError, 'no namespace for attribute prefix %s'\
  557. %prefix
  558. if not self.attributes.has_key(ns):
  559. self.attributes[ns] = {}
  560. elif self.attributes[ns].has_key(value):
  561. raise SchemaError, 'attribute %s declared multiple times in %s'\
  562. %(value, ns)
  563. self.attributes[ns][value] = v
  564. elif not self.attributes.has_key(value):
  565. self.attributes[value] = v
  566. else:
  567. raise SchemaError, 'attribute %s declared multiple times' %value
  568. if not isinstance(self, WSDLToolsAdapter):
  569. self.__checkAttributes()
  570. self.__setAttributeDefaults()
  571. #set QNames
  572. for k in ['type', 'element', 'base', 'ref', 'substitutionGroup', 'itemType']:
  573. if self.attributes.has_key(k):
  574. prefix, value = SplitQName(self.attributes.get(k))
  575. self.attributes[k] = \
  576. TypeDescriptionComponent((self.getXMLNS(prefix), value))
  577. #Union, memberTypes is a whitespace separated list of QNames
  578. for k in ['memberTypes']:
  579. if self.attributes.has_key(k):
  580. qnames = self.attributes[k]
  581. self.attributes[k] = []
  582. for qname in qnames.split():
  583. prefix, value = SplitQName(qname)
  584. self.attributes['memberTypes'].append(\
  585. TypeDescriptionComponent(\
  586. (self.getXMLNS(prefix), value)))
  587. def getContents(self, node):
  588. """retrieve xsd contents
  589. """
  590. return node.getContentList(*self.__class__.contents['xsd'])
  591. def __setAttributeDefaults(self):
  592. """Looks for default values for unset attributes. If
  593. class variable representing attribute is None, then
  594. it must be defined as an instance variable.
  595. """
  596. for k,v in self.__class__.attributes.items():
  597. if v is not None and self.attributes.has_key(k) is False:
  598. if isinstance(v, types.FunctionType):
  599. self.attributes[k] = v(self)
  600. else:
  601. self.attributes[k] = v
  602. def __checkAttributes(self):
  603. """Checks that required attributes have been defined,
  604. attributes w/default cannot be required. Checks
  605. all defined attributes are legal, attribute
  606. references are not subject to this test.
  607. """
  608. for a in self.__class__.required:
  609. if not self.attributes.has_key(a):
  610. raise SchemaError,\
  611. 'class instance %s, missing required attribute %s'\
  612. %(self.__class__, a)
  613. for a in self.attributes.keys():
  614. if (a not in (XMLSchemaComponent.xmlns, XMLNS.XML)) and\
  615. (a not in self.__class__.attributes.keys()) and not\
  616. (self.isAttribute() and self.isReference()):
  617. raise SchemaError, '%s, unknown attribute(%s,%s)' \
  618. %(self.getItemTrace(), a, self.attributes[a])
  619. class WSDLToolsAdapter(XMLSchemaComponent):
  620. """WSDL Adapter to grab the attributes from the wsdl document node.
  621. """
  622. attributes = {'name':None, 'targetNamespace':None}
  623. tag = 'definitions'
  624. def __init__(self, wsdl):
  625. XMLSchemaComponent.__init__(self, parent=wsdl)
  626. self.setAttributes(DOMAdapter(wsdl.document))
  627. def getImportSchemas(self):
  628. """returns WSDLTools.WSDL types Collection
  629. """
  630. return self._parent().types
  631. class Notation(XMLSchemaComponent):
  632. """<notation>
  633. parent:
  634. schema
  635. attributes:
  636. id -- ID
  637. name -- NCName, Required
  638. public -- token, Required
  639. system -- anyURI
  640. contents:
  641. annotation?
  642. """
  643. required = ['name', 'public']
  644. attributes = {'id':None, 'name':None, 'public':None, 'system':None}
  645. contents = {'xsd':('annotation')}
  646. tag = 'notation'
  647. def __init__(self, parent):
  648. XMLSchemaComponent.__init__(self, parent)
  649. self.annotation = None
  650. def fromDom(self, node):
  651. self.setAttributes(node)
  652. contents = self.getContents(node)
  653. for i in contents:
  654. component = SplitQName(i.getTagName())[1]
  655. if component == 'annotation' and not self.annotation:
  656. self.annotation = Annotation(self)
  657. self.annotation.fromDom(i)
  658. else:
  659. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  660. class Annotation(XMLSchemaComponent):
  661. """<annotation>
  662. parent:
  663. all,any,anyAttribute,attribute,attributeGroup,choice,complexContent,
  664. complexType,element,extension,field,group,import,include,key,keyref,
  665. list,notation,redefine,restriction,schema,selector,simpleContent,
  666. simpleType,union,unique
  667. attributes:
  668. id -- ID
  669. contents:
  670. (documentation | appinfo)*
  671. """
  672. attributes = {'id':None}
  673. contents = {'xsd':('documentation', 'appinfo')}
  674. tag = 'annotation'
  675. def __init__(self, parent):
  676. XMLSchemaComponent.__init__(self, parent)
  677. self.content = None
  678. def fromDom(self, node):
  679. self.setAttributes(node)
  680. contents = self.getContents(node)
  681. content = []
  682. for i in contents:
  683. component = SplitQName(i.getTagName())[1]
  684. if component == 'documentation':
  685. #print_debug('class %s, documentation skipped' %self.__class__, 5)
  686. continue
  687. elif component == 'appinfo':
  688. #print_debug('class %s, appinfo skipped' %self.__class__, 5)
  689. continue
  690. else:
  691. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  692. self.content = tuple(content)
  693. class Documentation(XMLSchemaComponent):
  694. """<documentation>
  695. parent:
  696. annotation
  697. attributes:
  698. source, anyURI
  699. xml:lang, language
  700. contents:
  701. mixed, any
  702. """
  703. attributes = {'source':None, 'xml:lang':None}
  704. contents = {'xsd':('mixed', 'any')}
  705. tag = 'documentation'
  706. def __init__(self, parent):
  707. XMLSchemaComponent.__init__(self, parent)
  708. self.content = None
  709. def fromDom(self, node):
  710. self.setAttributes(node)
  711. contents = self.getContents(node)
  712. content = []
  713. for i in contents:
  714. component = SplitQName(i.getTagName())[1]
  715. if component == 'mixed':
  716. #print_debug('class %s, mixed skipped' %self.__class__, 5)
  717. continue
  718. elif component == 'any':
  719. #print_debug('class %s, any skipped' %self.__class__, 5)
  720. continue
  721. else:
  722. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  723. self.content = tuple(content)
  724. class Appinfo(XMLSchemaComponent):
  725. """<appinfo>
  726. parent:
  727. annotation
  728. attributes:
  729. source, anyURI
  730. contents:
  731. mixed, any
  732. """
  733. attributes = {'source':None, 'anyURI':None}
  734. contents = {'xsd':('mixed', 'any')}
  735. tag = 'appinfo'
  736. def __init__(self, parent):
  737. XMLSchemaComponent.__init__(self, parent)
  738. self.content = None
  739. def fromDom(self, node):
  740. self.setAttributes(node)
  741. contents = self.getContents(node)
  742. content = []
  743. for i in contents:
  744. component = SplitQName(i.getTagName())[1]
  745. if component == 'mixed':
  746. #print_debug('class %s, mixed skipped' %self.__class__, 5)
  747. continue
  748. elif component == 'any':
  749. #print_debug('class %s, any skipped' %self.__class__, 5)
  750. continue
  751. else:
  752. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  753. self.content = tuple(content)
  754. class XMLSchemaFake:
  755. # This is temporary, for the benefit of WSDL until the real thing works.
  756. def __init__(self, element):
  757. self.targetNamespace = DOM.getAttr(element, 'targetNamespace')
  758. self.element = element
  759. class XMLSchema(XMLSchemaComponent):
  760. """A schema is a collection of schema components derived from one
  761. or more schema documents, that is, one or more <schema> element
  762. information items. It represents the abstract notion of a schema
  763. rather than a single schema document (or other representation).
  764. <schema>
  765. parent:
  766. ROOT
  767. attributes:
  768. id -- ID
  769. version -- token
  770. xml:lang -- language
  771. targetNamespace -- anyURI
  772. attributeFormDefault -- 'qualified' | 'unqualified', 'unqualified'
  773. elementFormDefault -- 'qualified' | 'unqualified', 'unqualified'
  774. blockDefault -- '#all' | list of
  775. ('substitution | 'extension' | 'restriction')
  776. finalDefault -- '#all' | list of
  777. ('extension' | 'restriction' | 'list' | 'union')
  778. contents:
  779. ((include | import | redefine | annotation)*,
  780. (attribute, attributeGroup, complexType, element, group,
  781. notation, simpleType)*, annotation*)*
  782. attributes -- schema attributes
  783. imports -- import statements
  784. includes -- include statements
  785. redefines --
  786. types -- global simpleType, complexType definitions
  787. elements -- global element declarations
  788. attr_decl -- global attribute declarations
  789. attr_groups -- attribute Groups
  790. model_groups -- model Groups
  791. notations -- global notations
  792. """
  793. attributes = {'id':None,
  794. 'version':None,
  795. 'xml:lang':None,
  796. 'targetNamespace':None,
  797. 'attributeFormDefault':'unqualified',
  798. 'elementFormDefault':'unqualified',
  799. 'blockDefault':None,
  800. 'finalDefault':None}
  801. contents = {'xsd':('include', 'import', 'redefine', 'annotation',
  802. 'attribute', 'attributeGroup', 'complexType',
  803. 'element', 'group', 'notation', 'simpleType',
  804. 'annotation')}
  805. empty_namespace = ''
  806. tag = 'schema'
  807. def __init__(self, parent=None):
  808. """parent --
  809. instance variables:
  810. targetNamespace -- schema's declared targetNamespace, or empty string.
  811. _imported_schemas -- namespace keyed dict of schema dependencies, if
  812. a schema is provided instance will not resolve import statement.
  813. _included_schemas -- schemaLocation keyed dict of component schemas,
  814. if schema is provided instance will not resolve include statement.
  815. _base_url -- needed for relative URLs support, only works with URLs
  816. relative to initial document.
  817. includes -- collection of include statements
  818. imports -- collection of import statements
  819. elements -- collection of global element declarations
  820. types -- collection of global type definitions
  821. attr_decl -- collection of global attribute declarations
  822. attr_groups -- collection of global attribute group definitions
  823. model_groups -- collection of model group definitions
  824. notations -- collection of notations
  825. """
  826. self.__node = None
  827. self.targetNamespace = None
  828. XMLSchemaComponent.__init__(self, parent)
  829. f = lambda k: k.attributes['name']
  830. ns = lambda k: k.attributes['namespace']
  831. sl = lambda k: k.attributes['schemaLocation']
  832. self.includes = Collection(self, key=sl)
  833. self.imports = Collection(self, key=ns)
  834. self.elements = Collection(self, key=f)
  835. self.types = Collection(self, key=f)
  836. self.attr_decl = Collection(self, key=f)
  837. self.attr_groups = Collection(self, key=f)
  838. self.model_groups = Collection(self, key=f)
  839. self.notations = Collection(self, key=f)
  840. self._imported_schemas = {}
  841. self._included_schemas = {}
  842. self._base_url = None
  843. def getNode(self):
  844. """
  845. Interacting with the underlying DOM tree.
  846. """
  847. return self.__node
  848. def addImportSchema(self, schema):
  849. """for resolving import statements in Schema instance
  850. schema -- schema instance
  851. _imported_schemas
  852. """
  853. if not isinstance(schema, XMLSchema):
  854. raise TypeError, 'expecting a Schema instance'
  855. if schema.targetNamespace != self.targetNamespace:
  856. self._imported_schemas[schema.targetNamespace] = schema
  857. else:
  858. raise SchemaError, 'import schema bad targetNamespace'
  859. def addIncludeSchema(self, schemaLocation, schema):
  860. """for resolving include statements in Schema instance
  861. schemaLocation -- schema location
  862. schema -- schema instance
  863. _included_schemas
  864. """
  865. if not isinstance(schema, XMLSchema):
  866. raise TypeError, 'expecting a Schema instance'
  867. if not schema.targetNamespace or\
  868. schema.targetNamespace == self.targetNamespace:
  869. self._included_schemas[schemaLocation] = schema
  870. else:
  871. raise SchemaError, 'include schema bad targetNamespace'
  872. def setImportSchemas(self, schema_dict):
  873. """set the import schema dictionary, which is used to
  874. reference depedent schemas.
  875. """
  876. self._imported_schemas = schema_dict
  877. def getImportSchemas(self):
  878. """get the import schema dictionary, which is used to
  879. reference depedent schemas.
  880. """
  881. return self._imported_schemas
  882. def getSchemaNamespacesToImport(self):
  883. """returns tuple of namespaces the schema instance has declared
  884. itself to be depedent upon.
  885. """
  886. return tuple(self.includes.keys())
  887. def setIncludeSchemas(self, schema_dict):
  888. """set the include schema dictionary, which is keyed with
  889. schemaLocation (uri).
  890. This is a means of providing
  891. schemas to the current schema for content inclusion.
  892. """
  893. self._included_schemas = schema_dict
  894. def getIncludeSchemas(self):
  895. """get the include schema dictionary, which is keyed with
  896. schemaLocation (uri).
  897. """
  898. return self._included_schemas
  899. def getBaseUrl(self):
  900. """get base url, used for normalizing all relative uri's
  901. """
  902. return self._base_url
  903. def setBaseUrl(self, url):
  904. """set base url, used for normalizing all relative uri's
  905. """
  906. self._base_url = url
  907. def getElementFormDefault(self):
  908. """return elementFormDefault attribute
  909. """
  910. return self.attributes.get('elementFormDefault')
  911. def isElementFormDefaultQualified(self):
  912. return self.attributes.get('elementFormDefault') == 'qualified'
  913. def getAttributeFormDefault(self):
  914. """return attributeFormDefault attribute
  915. """
  916. return self.attributes.get('attributeFormDefault')
  917. def getBlockDefault(self):
  918. """return blockDefault attribute
  919. """
  920. return self.attributes.get('blockDefault')
  921. def getFinalDefault(self):
  922. """return finalDefault attribute
  923. """
  924. return self.attributes.get('finalDefault')
  925. def load(self, node, location=None):
  926. self.__node = node
  927. pnode = node.getParentNode()
  928. if pnode:
  929. pname = SplitQName(pnode.getTagName())[1]
  930. if pname == 'types':
  931. attributes = {}
  932. self.setAttributes(pnode)
  933. attributes.update(self.attributes)
  934. self.setAttributes(node)
  935. for k,v in attributes['xmlns'].items():
  936. if not self.attributes['xmlns'].has_key(k):
  937. self.attributes['xmlns'][k] = v
  938. else:
  939. self.setAttributes(node)
  940. else:
  941. self.setAttributes(node)
  942. self.targetNamespace = self.getTargetNamespace()
  943. for childNode in self.getContents(node):
  944. component = SplitQName(childNode.getTagName())[1]
  945. if component == 'include':
  946. tp = self.__class__.Include(self)
  947. tp.fromDom(childNode)
  948. sl = tp.attributes['schemaLocation']
  949. schema = tp.getSchema()
  950. if not self.getIncludeSchemas().has_key(sl):
  951. self.addIncludeSchema(sl, schema)
  952. self.includes[sl] = tp
  953. pn = childNode.getParentNode().getNode()
  954. pn.removeChild(childNode.getNode())
  955. for child in schema.getNode().getNode().childNodes:
  956. pn.appendChild(child.cloneNode(1))
  957. for collection in ['imports','elements','types',
  958. 'attr_decl','attr_groups','model_groups',
  959. 'notations']:
  960. for k,v in getattr(schema,collection).items():
  961. if not getattr(self,collection).has_key(k):
  962. v._parent = weakref.ref(self)
  963. getattr(self,collection)[k] = v
  964. else:
  965. print "Warning: Not keeping schema component."
  966. elif component == 'import':
  967. tp = self.__class__.Import(self)
  968. tp.fromDom(childNode)
  969. import_ns = tp.getAttribute('namespace') or \
  970. self.__class__.empty_namespace
  971. if not self.getImportSchemas().has_key(import_ns) and \
  972. tp.getAttribute('schemaLocation'):
  973. self.addImportSchema(tp.getSchema())
  974. self.imports[import_ns] = tp
  975. elif component == 'redefine':
  976. # redefine not implemented yet
  977. pass
  978. elif component == 'annotation':
  979. # annotation not implemented yet
  980. pass
  981. elif component == 'attribute':
  982. tp = AttributeDeclaration(self)
  983. tp.fromDom(childNode)
  984. self.attr_decl[tp.getAttribute('name')] = tp
  985. elif component == 'attributeGroup':
  986. tp = AttributeGroupDefinition(self)
  987. tp.fromDom(childNode)
  988. self.attr_groups[tp.getAttribute('name')] = tp
  989. elif component == 'element':
  990. tp = ElementDeclaration(self)
  991. tp.fromDom(childNode)
  992. self.elements[tp.getAttribute('name')] = tp
  993. elif component == 'group':
  994. tp = ModelGroupDefinition(self)
  995. tp.fromDom(childNode)
  996. self.model_groups[tp.getAttribute('name')] = tp
  997. elif component == 'notation':
  998. tp = Notation(self)
  999. tp.fromDom(childNode)
  1000. self.notations[tp.getAttribute('name')] = tp
  1001. elif component == 'complexType':
  1002. tp = ComplexType(self)
  1003. tp.fromDom(childNode)
  1004. self.types[tp.getAttribute('name')] = tp
  1005. elif component == 'simpleType':
  1006. tp = SimpleType(self)
  1007. tp.fromDom(childNode)
  1008. self.types[tp.getAttribute('name')] = tp
  1009. else:
  1010. break
  1011. # indx += 1
  1012. class Import(XMLSchemaComponent):
  1013. """<import>
  1014. parent:
  1015. schema
  1016. attributes:
  1017. id -- ID
  1018. namespace -- anyURI
  1019. schemaLocation -- anyURI
  1020. contents:
  1021. annotation?
  1022. """
  1023. attributes = {'id':None,
  1024. 'namespace':None,
  1025. 'schemaLocation':None}
  1026. contents = {'xsd':['annotation']}
  1027. tag = 'import'
  1028. def __init__(self, parent):
  1029. XMLSchemaComponent.__init__(self, parent)
  1030. self.annotation = None
  1031. self._schema = None
  1032. def fromDom(self, node):
  1033. self.setAttributes(node)
  1034. contents = self.getContents(node)
  1035. if self.attributes['namespace'] == self.getTargetNamespace():
  1036. raise SchemaError, 'namespace of schema and import match'
  1037. for i in contents:
  1038. component = SplitQName(i.getTagName())[1]
  1039. if component == 'annotation' and not self.annotation:
  1040. self.annotation = Annotation(self)
  1041. self.annotation.fromDom(i)
  1042. else:
  1043. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1044. def getSchema(self):
  1045. """if schema is not defined, first look for a Schema class instance
  1046. in parent Schema. Else if not defined resolve schemaLocation
  1047. and create a new Schema class instance, and keep a hard reference.
  1048. """
  1049. if not self._schema:
  1050. ns = self.attributes['namespace']
  1051. schema = self._parent().getImportSchemas().get(ns)
  1052. if not schema and self._parent()._parent:
  1053. schema = self._parent()._parent().getImportSchemas().get(ns)
  1054. if not schema:
  1055. url = self.attributes.get('schemaLocation')
  1056. if not url:
  1057. raise SchemaError, 'namespace(%s) is unknown' %ns
  1058. base_url = self._parent().getBaseUrl()
  1059. reader = SchemaReader(base_url=base_url)
  1060. reader._imports = self._parent().getImportSchemas()
  1061. reader._includes = self._parent().getIncludeSchemas()
  1062. self._schema = reader.loadFromURL(url)
  1063. return self._schema or schema
  1064. class Include(XMLSchemaComponent):
  1065. """<include schemaLocation>
  1066. parent:
  1067. schema
  1068. attributes:
  1069. id -- ID
  1070. schemaLocation -- anyURI, required
  1071. contents:
  1072. annotation?
  1073. """
  1074. required = ['schemaLocation']
  1075. attributes = {'id':None,
  1076. 'schemaLocation':None}
  1077. contents = {'xsd':['annotation']}
  1078. tag = 'include'
  1079. def __init__(self, parent):
  1080. XMLSchemaComponent.__init__(self, parent)
  1081. self.annotation = None
  1082. self._schema = None
  1083. def fromDom(self, node):
  1084. self.setAttributes(node)
  1085. contents = self.getContents(node)
  1086. for i in contents:
  1087. component = SplitQName(i.getTagName())[1]
  1088. if component == 'annotation' and not self.annotation:
  1089. self.annotation = Annotation(self)
  1090. self.annotation.fromDom(i)
  1091. else:
  1092. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1093. def getSchema(self):
  1094. """if schema is not defined, first look for a Schema class instance
  1095. in parent Schema. Else if not defined resolve schemaLocation
  1096. and create a new Schema class instance.
  1097. """
  1098. if not self._schema:
  1099. schema = self._parent()
  1100. self._schema = schema.getIncludeSchemas().get(\
  1101. self.attributes['schemaLocation']
  1102. )
  1103. if not self._schema:
  1104. url = self.attributes['schemaLocation']
  1105. reader = SchemaReader(base_url=schema.getBaseUrl())
  1106. reader._imports = schema.getImportSchemas()
  1107. reader._includes = schema.getIncludeSchemas()
  1108. self._schema = reader.loadFromURL(url)
  1109. return self._schema
  1110. class AttributeDeclaration(XMLSchemaComponent,\
  1111. AttributeMarker,\
  1112. DeclarationMarker):
  1113. """<attribute name>
  1114. parent:
  1115. schema
  1116. attributes:
  1117. id -- ID
  1118. name -- NCName, required
  1119. type -- QName
  1120. default -- string
  1121. fixed -- string
  1122. contents:
  1123. annotation?, simpleType?
  1124. """
  1125. required = ['name']
  1126. attributes = {'id':None,
  1127. 'name':None,
  1128. 'type':None,
  1129. 'default':None,
  1130. 'fixed':None}
  1131. contents = {'xsd':['annotation','simpleType']}
  1132. tag = 'attribute'
  1133. def __init__(self, parent):
  1134. XMLSchemaComponent.__init__(self, parent)
  1135. self.annotation = None
  1136. self.content = None
  1137. def fromDom(self, node):
  1138. """ No list or union support
  1139. """
  1140. self.setAttributes(node)
  1141. contents = self.getContents(node)
  1142. for i in contents:
  1143. component = SplitQName(i.getTagName())[1]
  1144. if component == 'annotation' and not self.annotation:
  1145. self.annotation = Annotation(self)
  1146. self.annotation.fromDom(i)
  1147. elif component == 'simpleType':
  1148. self.content = AnonymousSimpleType(self)
  1149. self.content.fromDom(i)
  1150. else:
  1151. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1152. class LocalAttributeDeclaration(AttributeDeclaration,\
  1153. AttributeMarker,\
  1154. LocalMarker,\
  1155. DeclarationMarker):
  1156. """<attribute name>
  1157. parent:
  1158. complexType, restriction, extension, attributeGroup
  1159. attributes:
  1160. id -- ID
  1161. name -- NCName, required
  1162. type -- QName
  1163. form -- ('qualified' | 'unqualified'), schema.attributeFormDefault
  1164. use -- ('optional' | 'prohibited' | 'required'), optional
  1165. default -- string
  1166. fixed -- string
  1167. contents:
  1168. annotation?, simpleType?
  1169. """
  1170. required = ['name']
  1171. attributes = {'id':None,
  1172. 'name':None,
  1173. 'type':None,
  1174. 'form':lambda self: GetSchema(self).getAttributeFormDefault(),
  1175. 'use':'optional',
  1176. 'default':None,
  1177. 'fixed':None}
  1178. contents = {'xsd':['annotation','simpleType']}
  1179. def __init__(self, parent):
  1180. AttributeDeclaration.__init__(self, parent)
  1181. self.annotation = None
  1182. self.content = None
  1183. def fromDom(self, node):
  1184. self.setAttributes(node)
  1185. contents = self.getContents(node)
  1186. for i in contents:
  1187. component = SplitQName(i.getTagName())[1]
  1188. if component == 'annotation' and not self.annotation:
  1189. self.annotation = Annotation(self)
  1190. self.annotation.fromDom(i)
  1191. elif component == 'simpleType':
  1192. self.content = AnonymousSimpleType(self)
  1193. self.content.fromDom(i)
  1194. else:
  1195. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1196. class AttributeWildCard(XMLSchemaComponent,\
  1197. AttributeMarker,\
  1198. DeclarationMarker,\
  1199. WildCardMarker):
  1200. """<anyAttribute>
  1201. parents:
  1202. complexType, restriction, extension, attributeGroup
  1203. attributes:
  1204. id -- ID
  1205. namespace -- '##any' | '##other' |
  1206. (anyURI* | '##targetNamespace' | '##local'), ##any
  1207. processContents -- 'lax' | 'skip' | 'strict', strict
  1208. contents:
  1209. annotation?
  1210. """
  1211. attributes = {'id':None,
  1212. 'namespace':'##any',
  1213. 'processContents':'strict'}
  1214. contents = {'xsd':['annotation']}
  1215. tag = 'anyAttribute'
  1216. def __init__(self, parent):
  1217. XMLSchemaComponent.__init__(self, parent)
  1218. self.annotation = None
  1219. def fromDom(self, node):
  1220. self.setAttributes(node)
  1221. contents = self.getContents(node)
  1222. for i in contents:
  1223. component = SplitQName(i.getTagName())[1]
  1224. if component == 'annotation' and not self.annotation:
  1225. self.annotation = Annotation(self)
  1226. self.annotation.fromDom(i)
  1227. else:
  1228. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1229. class AttributeReference(XMLSchemaComponent,\
  1230. AttributeMarker,\
  1231. ReferenceMarker):
  1232. """<attribute ref>
  1233. parents:
  1234. complexType, restriction, extension, attributeGroup
  1235. attributes:
  1236. id -- ID
  1237. ref -- QName, required
  1238. use -- ('optional' | 'prohibited' | 'required'), optional
  1239. default -- string
  1240. fixed -- string
  1241. contents:
  1242. annotation?
  1243. """
  1244. required = ['ref']
  1245. attributes = {'id':None,
  1246. 'ref':None,
  1247. 'use':'optional',
  1248. 'default':None,
  1249. 'fixed':None}
  1250. contents = {'xsd':['annotation']}
  1251. tag = 'attribute'
  1252. def __init__(self, parent):
  1253. XMLSchemaComponent.__init__(self, parent)
  1254. self.annotation = None
  1255. def getAttributeDeclaration(self, attribute='ref'):
  1256. return XMLSchemaComponent.getAttributeDeclaration(self, attribute)
  1257. def fromDom(self, node):
  1258. self.setAttributes(node)
  1259. contents = self.getContents(node)
  1260. for i in contents:
  1261. component = SplitQName(i.getTagName())[1]
  1262. if component == 'annotation' and not self.annotation:
  1263. self.annotation = Annotation(self)
  1264. self.annotation.fromDom(i)
  1265. else:
  1266. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1267. class AttributeGroupDefinition(XMLSchemaComponent,\
  1268. AttributeGroupMarker,\
  1269. DefinitionMarker):
  1270. """<attributeGroup name>
  1271. parents:
  1272. schema, redefine
  1273. attributes:
  1274. id -- ID
  1275. name -- NCName, required
  1276. contents:
  1277. annotation?, (attribute | attributeGroup)*, anyAttribute?
  1278. """
  1279. required = ['name']
  1280. attributes = {'id':None,
  1281. 'name':None}
  1282. contents = {'xsd':['annotation', 'attribute', 'attributeGroup', 'anyAttribute']}
  1283. tag = 'attributeGroup'
  1284. def __init__(self, parent):
  1285. XMLSchemaComponent.__init__(self, parent)
  1286. self.annotation = None
  1287. self.attr_content = None
  1288. def getAttributeContent(self):
  1289. return self.attr_content
  1290. def fromDom(self, node):
  1291. self.setAttributes(node)
  1292. contents = self.getContents(node)
  1293. content = []
  1294. for indx in range(len(contents)):
  1295. component = SplitQName(contents[indx].getTagName())[1]
  1296. if (component == 'annotation') and (not indx):
  1297. self.annotation = Annotation(self)
  1298. self.annotation.fromDom(contents[indx])
  1299. elif component == 'attribute':
  1300. if contents[indx].hasattr('name'):
  1301. content.append(LocalAttributeDeclaration(self))
  1302. elif contents[indx].hasattr('ref'):
  1303. content.append(AttributeReference(self))
  1304. else:
  1305. raise SchemaError, 'Unknown attribute type'
  1306. content[-1].fromDom(contents[indx])
  1307. elif component == 'attributeGroup':
  1308. content.append(AttributeGroupReference(self))
  1309. content[-1].fromDom(contents[indx])
  1310. elif component == 'anyAttribute':
  1311. if len(contents) != indx+1:
  1312. raise SchemaError, 'anyAttribute is out of order in %s' %self.getItemTrace()
  1313. content.append(AttributeWildCard(self))
  1314. content[-1].fromDom(contents[indx])
  1315. else:
  1316. raise SchemaError, 'Unknown component (%s)' %(contents[indx].getTagName())
  1317. self.attr_content = tuple(content)
  1318. class AttributeGroupReference(XMLSchemaComponent,\
  1319. AttributeGroupMarker,\
  1320. ReferenceMarker):
  1321. """<attributeGroup ref>
  1322. parents:
  1323. complexType, restriction, extension, attributeGroup
  1324. attributes:
  1325. id -- ID
  1326. ref -- QName, required
  1327. contents:
  1328. annotation?
  1329. """
  1330. required = ['ref']
  1331. attributes = {'id':None,
  1332. 'ref':None}
  1333. contents = {'xsd':['annotation']}
  1334. tag = 'attributeGroup'
  1335. def __init__(self, parent):
  1336. XMLSchemaComponent.__init__(self, parent)
  1337. self.annotation = None
  1338. def getAttributeGroup(self, attribute='ref'):
  1339. """attribute -- attribute with a QName value (eg. type).
  1340. collection -- check types collection in parent Schema instance
  1341. """
  1342. return XMLSchemaComponent.getAttributeGroup(self, attribute)
  1343. def fromDom(self, node):
  1344. self.setAttributes(node)
  1345. contents = self.getContents(node)
  1346. for i in contents:
  1347. component = SplitQName(i.getTagName())[1]
  1348. if component == 'annotation' and not self.annotation:
  1349. self.annotation = Annotation(self)
  1350. self.annotation.fromDom(i)
  1351. else:
  1352. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1353. ######################################################
  1354. # Elements
  1355. #####################################################
  1356. class IdentityConstrants(XMLSchemaComponent):
  1357. """Allow one to uniquely identify nodes in a document and ensure the
  1358. integrity of references between them.
  1359. attributes -- dictionary of attributes
  1360. selector -- XPath to selected nodes
  1361. fields -- list of XPath to key field
  1362. """
  1363. def __init__(self, parent):
  1364. XMLSchemaComponent.__init__(self, parent)
  1365. self.selector = None
  1366. self.fields = None
  1367. self.annotation = None
  1368. def fromDom(self, node):
  1369. self.setAttributes(node)
  1370. contents = self.getContents(node)
  1371. fields = []
  1372. for i in contents:
  1373. component = SplitQName(i.getTagName())[1]
  1374. if component in self.__class__.contents['xsd']:
  1375. if component == 'annotation' and not self.annotation:
  1376. self.annotation = Annotation(self)
  1377. self.annotation.fromDom(i)
  1378. elif component == 'selector':
  1379. self.selector = self.Selector(self)
  1380. self.selector.fromDom(i)
  1381. continue
  1382. elif component == 'field':
  1383. fields.append(self.Field(self))
  1384. fields[-1].fromDom(i)
  1385. continue
  1386. else:
  1387. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1388. else:
  1389. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1390. self.fields = tuple(fields)
  1391. class Constraint(XMLSchemaComponent):
  1392. def __init__(self, parent):
  1393. XMLSchemaComponent.__init__(self, parent)
  1394. self.annotation = None
  1395. def fromDom(self, node):
  1396. self.setAttributes(node)
  1397. contents = self.getContents(node)
  1398. for i in contents:
  1399. component = SplitQName(i.getTagName())[1]
  1400. if component in self.__class__.contents['xsd']:
  1401. if component == 'annotation' and not self.annotation:
  1402. self.annotation = Annotation(self)
  1403. self.annotation.fromDom(i)
  1404. else:
  1405. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1406. else:
  1407. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1408. class Selector(Constraint):
  1409. """<selector xpath>
  1410. parent:
  1411. unique, key, keyref
  1412. attributes:
  1413. id -- ID
  1414. xpath -- XPath subset, required
  1415. contents:
  1416. annotation?
  1417. """
  1418. required = ['xpath']
  1419. attributes = {'id':None,
  1420. 'xpath':None}
  1421. contents = {'xsd':['annotation']}
  1422. tag = 'selector'
  1423. class Field(Constraint):
  1424. """<field xpath>
  1425. parent:
  1426. unique, key, keyref
  1427. attributes:
  1428. id -- ID
  1429. xpath -- XPath subset, required
  1430. contents:
  1431. annotation?
  1432. """
  1433. required = ['xpath']
  1434. attributes = {'id':None,
  1435. 'xpath':None}
  1436. contents = {'xsd':['annotation']}
  1437. tag = 'field'
  1438. class Unique(IdentityConstrants):
  1439. """<unique name> Enforce fields are unique w/i a specified scope.
  1440. parent:
  1441. element
  1442. attributes:
  1443. id -- ID
  1444. name -- NCName, required
  1445. contents:
  1446. annotation?, selector, field+
  1447. """
  1448. required = ['name']
  1449. attributes = {'id':None,
  1450. 'name':None}
  1451. contents = {'xsd':['annotation', 'selector', 'field']}
  1452. tag = 'unique'
  1453. class Key(IdentityConstrants):
  1454. """<key name> Enforce fields are unique w/i a specified scope, and all
  1455. field values are present w/i document. Fields cannot
  1456. be nillable.
  1457. parent:
  1458. element
  1459. attributes:
  1460. id -- ID
  1461. name -- NCName, required
  1462. contents:
  1463. annotation?, selector, field+
  1464. """
  1465. required = ['name']
  1466. attributes = {'id':None,
  1467. 'name':None}
  1468. contents = {'xsd':['annotation', 'selector', 'field']}
  1469. tag = 'key'
  1470. class KeyRef(IdentityConstrants):
  1471. """<keyref name refer> Ensure a match between two sets of values in an
  1472. instance.
  1473. parent:
  1474. element
  1475. attributes:
  1476. id -- ID
  1477. name -- NCName, required
  1478. refer -- QName, required
  1479. contents:
  1480. annotation?, selector, field+
  1481. """
  1482. required = ['name', 'refer']
  1483. attributes = {'id':None,
  1484. 'name':None,
  1485. 'refer':None}
  1486. contents = {'xsd':['annotation', 'selector', 'field']}
  1487. tag = 'keyref'
  1488. class ElementDeclaration(XMLSchemaComponent,\
  1489. ElementMarker,\
  1490. DeclarationMarker):
  1491. """<element name>
  1492. parents:
  1493. schema
  1494. attributes:
  1495. id -- ID
  1496. name -- NCName, required
  1497. type -- QName
  1498. default -- string
  1499. fixed -- string
  1500. nillable -- boolean, false
  1501. abstract -- boolean, false
  1502. substitutionGroup -- QName
  1503. block -- ('#all' | ('substition' | 'extension' | 'restriction')*),
  1504. schema.blockDefault
  1505. final -- ('#all' | ('extension' | 'restriction')*),
  1506. schema.finalDefault
  1507. contents:
  1508. annotation?, (simpleType,complexType)?, (key | keyref | unique)*
  1509. """
  1510. required = ['name']
  1511. attributes = {'id':None,
  1512. 'name':None,
  1513. 'type':None,
  1514. 'default':None,
  1515. 'fixed':None,
  1516. 'nillable':0,
  1517. 'abstract':0,
  1518. 'substitutionGroup':None,
  1519. 'block':lambda self: self._parent().getBlockDefault(),
  1520. 'final':lambda self: self._parent().getFinalDefault()}
  1521. contents = {'xsd':['annotation', 'simpleType', 'complexType', 'key',\
  1522. 'keyref', 'unique']}
  1523. tag = 'element'
  1524. def __init__(self, parent):
  1525. XMLSchemaComponent.__init__(self, parent)
  1526. self.annotation = None
  1527. self.content = None
  1528. self.constraints = ()
  1529. def isQualified(self):
  1530. """
  1531. Global elements are always qualified.
  1532. """
  1533. return True
  1534. def getElementDeclaration(self, attribute):
  1535. raise Warning, 'invalid operation for <%s>' %self.tag
  1536. def getTypeDefinition(self, attribute=None):
  1537. """
  1538. If attribute is None, "type" is assumed, return the corresponding
  1539. representation of the global type definition (TypeDefinition),
  1540. or the local definition if don't find "type". To maintain backwards
  1541. compat, if attribute is provided call base class method.
  1542. """
  1543. if attribute:
  1544. return XMLSchemaComponent.getTypeDefinition(self, attribute)
  1545. gt = XMLSchemaComponent.getTypeDefinition(self, 'type')
  1546. if gt:
  1547. return gt
  1548. return self.content
  1549. def getConstraints(self):
  1550. return self._constraints
  1551. def setConstraints(self, constraints):
  1552. self._constraints = tuple(constraints)
  1553. constraints = property(getConstraints, setConstraints, None, "tuple of key, keyref, unique constraints")
  1554. def fromDom(self, node):
  1555. self.setAttributes(node)
  1556. contents = self.getContents(node)
  1557. constraints = []
  1558. for i in contents:
  1559. component = SplitQName(i.getTagName())[1]
  1560. if component in self.__class__.contents['xsd']:
  1561. if component == 'annotation' and not self.annotation:
  1562. self.annotation = Annotation(self)
  1563. self.annotation.fromDom(i)
  1564. elif component == 'simpleType' and not self.content:
  1565. self.content = AnonymousSimpleType(self)
  1566. self.content.fromDom(i)
  1567. elif component == 'complexType' and not self.content:
  1568. self.content = LocalComplexType(self)
  1569. self.content.fromDom(i)
  1570. elif component == 'key':
  1571. constraints.append(Key(self))
  1572. constraints[-1].fromDom(i)
  1573. elif component == 'keyref':
  1574. constraints.append(KeyRef(self))
  1575. constraints[-1].fromDom(i)
  1576. elif component == 'unique':
  1577. constraints.append(Unique(self))
  1578. constraints[-1].fromDom(i)
  1579. else:
  1580. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1581. else:
  1582. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1583. self.constraints = constraints
  1584. class LocalElementDeclaration(ElementDeclaration,\
  1585. LocalMarker):
  1586. """<element>
  1587. parents:
  1588. all, choice, sequence
  1589. attributes:
  1590. id -- ID
  1591. name -- NCName, required
  1592. form -- ('qualified' | 'unqualified'), schema.elementFormDefault
  1593. type -- QName
  1594. minOccurs -- Whole Number, 1
  1595. maxOccurs -- (Whole Number | 'unbounded'), 1
  1596. default -- string
  1597. fixed -- string
  1598. nillable -- boolean, false
  1599. block -- ('#all' | ('extension' | 'restriction')*), schema.blockDefault
  1600. contents:
  1601. annotation?, (simpleType,complexType)?, (key | keyref | unique)*
  1602. """
  1603. required = ['name']
  1604. attributes = {'id':None,
  1605. 'name':None,
  1606. 'form':lambda self: GetSchema(self).getElementFormDefault(),
  1607. 'type':None,
  1608. 'minOccurs':'1',
  1609. 'maxOccurs':'1',
  1610. 'default':None,
  1611. 'fixed':None,
  1612. 'nillable':0,
  1613. 'abstract':0,
  1614. 'block':lambda self: GetSchema(self).getBlockDefault()}
  1615. contents = {'xsd':['annotation', 'simpleType', 'complexType', 'key',\
  1616. 'keyref', 'unique']}
  1617. def isQualified(self):
  1618. """
  1619. Local elements can be qualified or unqualifed according
  1620. to the attribute form, or the elementFormDefault. By default
  1621. local elements are unqualified.
  1622. """
  1623. form = self.getAttribute('form')
  1624. if form == 'qualified':
  1625. return True
  1626. if form == 'unqualified':
  1627. return False
  1628. raise SchemaError, 'Bad form (%s) for element: %s' %(form, self.getItemTrace())
  1629. class ElementReference(XMLSchemaComponent,\
  1630. ElementMarker,\
  1631. ReferenceMarker):
  1632. """<element ref>
  1633. parents:
  1634. all, choice, sequence
  1635. attributes:
  1636. id -- ID
  1637. ref -- QName, required
  1638. minOccurs -- Whole Number, 1
  1639. maxOccurs -- (Whole Number | 'unbounded'), 1
  1640. contents:
  1641. annotation?
  1642. """
  1643. required = ['ref']
  1644. attributes = {'id':None,
  1645. 'ref':None,
  1646. 'minOccurs':'1',
  1647. 'maxOccurs':'1'}
  1648. contents = {'xsd':['annotation']}
  1649. tag = 'element'
  1650. def __init__(self, parent):
  1651. XMLSchemaComponent.__init__(self, parent)
  1652. self.annotation = None
  1653. def getElementDeclaration(self, attribute=None):
  1654. """If attribute is None, "ref" is assumed, return the corresponding
  1655. representation of the global element declaration (ElementDeclaration),
  1656. To maintain backwards compat, if attribute is provided call base class method.
  1657. """
  1658. if attribute:
  1659. return XMLSchemaComponent.getElementDeclaration(self, attribute)
  1660. return XMLSchemaComponent.getElementDeclaration(self, 'ref')
  1661. def fromDom(self, node):
  1662. self.annotation = None
  1663. self.setAttributes(node)
  1664. for i in self.getContents(node):
  1665. component = SplitQName(i.getTagName())[1]
  1666. if component in self.__class__.contents['xsd']:
  1667. if component == 'annotation' and not self.annotation:
  1668. self.annotation = Annotation(self)
  1669. self.annotation.fromDom(i)
  1670. else:
  1671. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1672. class ElementWildCard(LocalElementDeclaration, WildCardMarker):
  1673. """<any>
  1674. parents:
  1675. choice, sequence
  1676. attributes:
  1677. id -- ID
  1678. minOccurs -- Whole Number, 1
  1679. maxOccurs -- (Whole Number | 'unbounded'), 1
  1680. namespace -- '##any' | '##other' |
  1681. (anyURI* | '##targetNamespace' | '##local'), ##any
  1682. processContents -- 'lax' | 'skip' | 'strict', strict
  1683. contents:
  1684. annotation?
  1685. """
  1686. required = []
  1687. attributes = {'id':None,
  1688. 'minOccurs':'1',
  1689. 'maxOccurs':'1',
  1690. 'namespace':'##any',
  1691. 'processContents':'strict'}
  1692. contents = {'xsd':['annotation']}
  1693. tag = 'any'
  1694. def __init__(self, parent):
  1695. XMLSchemaComponent.__init__(self, parent)
  1696. self.annotation = None
  1697. def isQualified(self):
  1698. """
  1699. Global elements are always qualified, but if processContents
  1700. are not strict could have dynamically generated local elements.
  1701. """
  1702. return GetSchema(self).isElementFormDefaultQualified()
  1703. def getTypeDefinition(self, attribute):
  1704. raise Warning, 'invalid operation for <%s>' % self.tag
  1705. def fromDom(self, node):
  1706. self.annotation = None
  1707. self.setAttributes(node)
  1708. for i in self.getContents(node):
  1709. component = SplitQName(i.getTagName())[1]
  1710. if component in self.__class__.contents['xsd']:
  1711. if component == 'annotation' and not self.annotation:
  1712. self.annotation = Annotation(self)
  1713. self.annotation.fromDom(i)
  1714. else:
  1715. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1716. ######################################################
  1717. # Model Groups
  1718. #####################################################
  1719. class Sequence(XMLSchemaComponent,\
  1720. SequenceMarker):
  1721. """<sequence>
  1722. parents:
  1723. complexType, extension, restriction, group, choice, sequence
  1724. attributes:
  1725. id -- ID
  1726. minOccurs -- Whole Number, 1
  1727. maxOccurs -- (Whole Number | 'unbounded'), 1
  1728. contents:
  1729. annotation?, (element | group | choice | sequence | any)*
  1730. """
  1731. attributes = {'id':None,
  1732. 'minOccurs':'1',
  1733. 'maxOccurs':'1'}
  1734. contents = {'xsd':['annotation', 'element', 'group', 'choice', 'sequence',\
  1735. 'any']}
  1736. tag = 'sequence'
  1737. def __init__(self, parent):
  1738. XMLSchemaComponent.__init__(self, parent)
  1739. self.annotation = None
  1740. self.content = None
  1741. def fromDom(self, node):
  1742. self.setAttributes(node)
  1743. contents = self.getContents(node)
  1744. content = []
  1745. for i in contents:
  1746. component = SplitQName(i.getTagName())[1]
  1747. if component in self.__class__.contents['xsd']:
  1748. if component == 'annotation' and not self.annotation:
  1749. self.annotation = Annotation(self)
  1750. self.annotation.fromDom(i)
  1751. continue
  1752. elif component == 'element':
  1753. if i.hasattr('ref'):
  1754. content.append(ElementReference(self))
  1755. else:
  1756. content.append(LocalElementDeclaration(self))
  1757. elif component == 'group':
  1758. content.append(ModelGroupReference(self))
  1759. elif component == 'choice':
  1760. content.append(Choice(self))
  1761. elif component == 'sequence':
  1762. content.append(Sequence(self))
  1763. elif component == 'any':
  1764. content.append(ElementWildCard(self))
  1765. else:
  1766. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1767. content[-1].fromDom(i)
  1768. else:
  1769. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1770. self.content = tuple(content)
  1771. class All(XMLSchemaComponent,\
  1772. AllMarker):
  1773. """<all>
  1774. parents:
  1775. complexType, extension, restriction, group
  1776. attributes:
  1777. id -- ID
  1778. minOccurs -- '0' | '1', 1
  1779. maxOccurs -- '1', 1
  1780. contents:
  1781. annotation?, element*
  1782. """
  1783. attributes = {'id':None,
  1784. 'minOccurs':'1',
  1785. 'maxOccurs':'1'}
  1786. contents = {'xsd':['annotation', 'element']}
  1787. tag = 'all'
  1788. def __init__(self, parent):
  1789. XMLSchemaComponent.__init__(self, parent)
  1790. self.annotation = None
  1791. self.content = None
  1792. def fromDom(self, node):
  1793. self.setAttributes(node)
  1794. contents = self.getContents(node)
  1795. content = []
  1796. for i in contents:
  1797. component = SplitQName(i.getTagName())[1]
  1798. if component in self.__class__.contents['xsd']:
  1799. if component == 'annotation' and not self.annotation:
  1800. self.annotation = Annotation(self)
  1801. self.annotation.fromDom(i)
  1802. continue
  1803. elif component == 'element':
  1804. if i.hasattr('ref'):
  1805. content.append(ElementReference(self))
  1806. else:
  1807. content.append(LocalElementDeclaration(self))
  1808. else:
  1809. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1810. content[-1].fromDom(i)
  1811. else:
  1812. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1813. self.content = tuple(content)
  1814. class Choice(XMLSchemaComponent,\
  1815. ChoiceMarker):
  1816. """<choice>
  1817. parents:
  1818. complexType, extension, restriction, group, choice, sequence
  1819. attributes:
  1820. id -- ID
  1821. minOccurs -- Whole Number, 1
  1822. maxOccurs -- (Whole Number | 'unbounded'), 1
  1823. contents:
  1824. annotation?, (element | group | choice | sequence | any)*
  1825. """
  1826. attributes = {'id':None,
  1827. 'minOccurs':'1',
  1828. 'maxOccurs':'1'}
  1829. contents = {'xsd':['annotation', 'element', 'group', 'choice', 'sequence',\
  1830. 'any']}
  1831. tag = 'choice'
  1832. def __init__(self, parent):
  1833. XMLSchemaComponent.__init__(self, parent)
  1834. self.annotation = None
  1835. self.content = None
  1836. def fromDom(self, node):
  1837. self.setAttributes(node)
  1838. contents = self.getContents(node)
  1839. content = []
  1840. for i in contents:
  1841. component = SplitQName(i.getTagName())[1]
  1842. if component in self.__class__.contents['xsd']:
  1843. if component == 'annotation' and not self.annotation:
  1844. self.annotation = Annotation(self)
  1845. self.annotation.fromDom(i)
  1846. continue
  1847. elif component == 'element':
  1848. if i.hasattr('ref'):
  1849. content.append(ElementReference(self))
  1850. else:
  1851. content.append(LocalElementDeclaration(self))
  1852. elif component == 'group':
  1853. content.append(ModelGroupReference(self))
  1854. elif component == 'choice':
  1855. content.append(Choice(self))
  1856. elif component == 'sequence':
  1857. content.append(Sequence(self))
  1858. elif component == 'any':
  1859. content.append(ElementWildCard(self))
  1860. else:
  1861. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1862. content[-1].fromDom(i)
  1863. else:
  1864. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1865. self.content = tuple(content)
  1866. class ModelGroupDefinition(XMLSchemaComponent,\
  1867. ModelGroupMarker,\
  1868. DefinitionMarker):
  1869. """<group name>
  1870. parents:
  1871. redefine, schema
  1872. attributes:
  1873. id -- ID
  1874. name -- NCName, required
  1875. contents:
  1876. annotation?, (all | choice | sequence)?
  1877. """
  1878. required = ['name']
  1879. attributes = {'id':None,
  1880. 'name':None}
  1881. contents = {'xsd':['annotation', 'all', 'choice', 'sequence']}
  1882. tag = 'group'
  1883. def __init__(self, parent):
  1884. XMLSchemaComponent.__init__(self, parent)
  1885. self.annotation = None
  1886. self.content = None
  1887. def fromDom(self, node):
  1888. self.setAttributes(node)
  1889. contents = self.getContents(node)
  1890. for i in contents:
  1891. component = SplitQName(i.getTagName())[1]
  1892. if component in self.__class__.contents['xsd']:
  1893. if component == 'annotation' and not self.annotation:
  1894. self.annotation = Annotation(self)
  1895. self.annotation.fromDom(i)
  1896. continue
  1897. elif component == 'all' and not self.content:
  1898. self.content = All(self)
  1899. elif component == 'choice' and not self.content:
  1900. self.content = Choice(self)
  1901. elif component == 'sequence' and not self.content:
  1902. self.content = Sequence(self)
  1903. else:
  1904. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1905. self.content.fromDom(i)
  1906. else:
  1907. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1908. class ModelGroupReference(XMLSchemaComponent,\
  1909. ModelGroupMarker,\
  1910. ReferenceMarker):
  1911. """<group ref>
  1912. parents:
  1913. choice, complexType, extension, restriction, sequence
  1914. attributes:
  1915. id -- ID
  1916. ref -- NCName, required
  1917. minOccurs -- Whole Number, 1
  1918. maxOccurs -- (Whole Number | 'unbounded'), 1
  1919. contents:
  1920. annotation?
  1921. """
  1922. required = ['ref']
  1923. attributes = {'id':None,
  1924. 'ref':None,
  1925. 'minOccurs':'1',
  1926. 'maxOccurs':'1'}
  1927. contents = {'xsd':['annotation']}
  1928. tag = 'group'
  1929. def __init__(self, parent):
  1930. XMLSchemaComponent.__init__(self, parent)
  1931. self.annotation = None
  1932. def getModelGroupReference(self):
  1933. return self.getModelGroup('ref')
  1934. def fromDom(self, node):
  1935. self.setAttributes(node)
  1936. contents = self.getContents(node)
  1937. for i in contents:
  1938. component = SplitQName(i.getTagName())[1]
  1939. if component in self.__class__.contents['xsd']:
  1940. if component == 'annotation' and not self.annotation:
  1941. self.annotation = Annotation(self)
  1942. self.annotation.fromDom(i)
  1943. else:
  1944. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1945. else:
  1946. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  1947. class ComplexType(XMLSchemaComponent,\
  1948. DefinitionMarker,\
  1949. ComplexMarker):
  1950. """<complexType name>
  1951. parents:
  1952. redefine, schema
  1953. attributes:
  1954. id -- ID
  1955. name -- NCName, required
  1956. mixed -- boolean, false
  1957. abstract -- boolean, false
  1958. block -- ('#all' | ('extension' | 'restriction')*), schema.blockDefault
  1959. final -- ('#all' | ('extension' | 'restriction')*), schema.finalDefault
  1960. contents:
  1961. annotation?, (simpleContent | complexContent |
  1962. ((group | all | choice | sequence)?, (attribute | attributeGroup)*, anyAttribute?))
  1963. """
  1964. required = ['name']
  1965. attributes = {'id':None,
  1966. 'name':None,
  1967. 'mixed':0,
  1968. 'abstract':0,
  1969. 'block':lambda self: self._parent().getBlockDefault(),
  1970. 'final':lambda self: self._parent().getFinalDefault()}
  1971. contents = {'xsd':['annotation', 'simpleContent', 'complexContent',\
  1972. 'group', 'all', 'choice', 'sequence', 'attribute', 'attributeGroup',\
  1973. 'anyAttribute', 'any']}
  1974. tag = 'complexType'
  1975. def __init__(self, parent):
  1976. XMLSchemaComponent.__init__(self, parent)
  1977. self.annotation = None
  1978. self.content = None
  1979. self.attr_content = None
  1980. def isMixed(self):
  1981. m = self.getAttribute('mixed')
  1982. if m == 0 or m == False:
  1983. return False
  1984. if isinstance(m, basestring) is True:
  1985. if m in ('false', '0'):
  1986. return False
  1987. if m in ('true', '1'):
  1988. return True
  1989. raise SchemaError, 'invalid value for attribute mixed(%s): %s'\
  1990. %(m, self.getItemTrace())
  1991. def getAttributeContent(self):
  1992. return self.attr_content
  1993. def getElementDeclaration(self, attribute):
  1994. raise Warning, 'invalid operation for <%s>' %self.tag
  1995. def getTypeDefinition(self, attribute):
  1996. raise Warning, 'invalid operation for <%s>' %self.tag
  1997. def fromDom(self, node):
  1998. self.setAttributes(node)
  1999. contents = self.getContents(node)
  2000. indx = 0
  2001. num = len(contents)
  2002. #XXX ugly
  2003. if not num:
  2004. return
  2005. component = SplitQName(contents[indx].getTagName())[1]
  2006. if component == 'annotation':
  2007. self.annotation = Annotation(self)
  2008. self.annotation.fromDom(contents[indx])
  2009. indx += 1
  2010. component = SplitQName(contents[indx].getTagName())[1]
  2011. self.content = None
  2012. if component == 'simpleContent':
  2013. self.content = self.__class__.SimpleContent(self)
  2014. self.content.fromDom(contents[indx])
  2015. elif component == 'complexContent':
  2016. self.content = self.__class__.ComplexContent(self)
  2017. self.content.fromDom(contents[indx])
  2018. else:
  2019. if component == 'all':
  2020. self.content = All(self)
  2021. elif component == 'choice':
  2022. self.content = Choice(self)
  2023. elif component == 'sequence':
  2024. self.content = Sequence(self)
  2025. elif component == 'group':
  2026. self.content = ModelGroupReference(self)
  2027. if self.content:
  2028. self.content.fromDom(contents[indx])
  2029. indx += 1
  2030. self.attr_content = []
  2031. while indx < num:
  2032. component = SplitQName(contents[indx].getTagName())[1]
  2033. if component == 'attribute':
  2034. if contents[indx].hasattr('ref'):
  2035. self.attr_content.append(AttributeReference(self))
  2036. else:
  2037. self.attr_content.append(LocalAttributeDeclaration(self))
  2038. elif component == 'attributeGroup':
  2039. self.attr_content.append(AttributeGroupReference(self))
  2040. elif component == 'anyAttribute':
  2041. self.attr_content.append(AttributeWildCard(self))
  2042. else:
  2043. raise SchemaError, 'Unknown component (%s): %s' \
  2044. %(contents[indx].getTagName(),self.getItemTrace())
  2045. self.attr_content[-1].fromDom(contents[indx])
  2046. indx += 1
  2047. class _DerivedType(XMLSchemaComponent):
  2048. def __init__(self, parent):
  2049. XMLSchemaComponent.__init__(self, parent)
  2050. self.annotation = None
  2051. # XXX remove attribute derivation, inconsistent
  2052. self.derivation = None
  2053. self.content = None
  2054. def fromDom(self, node):
  2055. self.setAttributes(node)
  2056. contents = self.getContents(node)
  2057. for i in contents:
  2058. component = SplitQName(i.getTagName())[1]
  2059. if component in self.__class__.contents['xsd']:
  2060. if component == 'annotation' and not self.annotation:
  2061. self.annotation = Annotation(self)
  2062. self.annotation.fromDom(i)
  2063. continue
  2064. elif component == 'restriction' and not self.derivation:
  2065. self.derivation = self.__class__.Restriction(self)
  2066. elif component == 'extension' and not self.derivation:
  2067. self.derivation = self.__class__.Extension(self)
  2068. else:
  2069. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  2070. else:
  2071. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  2072. self.derivation.fromDom(i)
  2073. self.content = self.derivation
  2074. class ComplexContent(_DerivedType,\
  2075. ComplexMarker):
  2076. """<complexContent>
  2077. parents:
  2078. complexType
  2079. attributes:
  2080. id -- ID
  2081. mixed -- boolean, false
  2082. contents:
  2083. annotation?, (restriction | extension)
  2084. """
  2085. attributes = {'id':None,
  2086. 'mixed':0}
  2087. contents = {'xsd':['annotation', 'restriction', 'extension']}
  2088. tag = 'complexContent'
  2089. def isMixed(self):
  2090. m = self.getAttribute('mixed')
  2091. if m == 0 or m == False:
  2092. return False
  2093. if isinstance(m, basestring) is True:
  2094. if m in ('false', '0'):
  2095. return False
  2096. if m in ('true', '1'):
  2097. return True
  2098. raise SchemaError, 'invalid value for attribute mixed(%s): %s'\
  2099. %(m, self.getItemTrace())
  2100. class _DerivationBase(XMLSchemaComponent):
  2101. """<extension>,<restriction>
  2102. parents:
  2103. complexContent
  2104. attributes:
  2105. id -- ID
  2106. base -- QName, required
  2107. contents:
  2108. annotation?, (group | all | choice | sequence)?,
  2109. (attribute | attributeGroup)*, anyAttribute?
  2110. """
  2111. required = ['base']
  2112. attributes = {'id':None,
  2113. 'base':None }
  2114. contents = {'xsd':['annotation', 'group', 'all', 'choice',\
  2115. 'sequence', 'attribute', 'attributeGroup', 'anyAttribute']}
  2116. def __init__(self, parent):
  2117. XMLSchemaComponent.__init__(self, parent)
  2118. self.annotation = None
  2119. self.content = None
  2120. self.attr_content = None
  2121. def getAttributeContent(self):
  2122. return self.attr_content
  2123. def fromDom(self, node):
  2124. self.setAttributes(node)
  2125. contents = self.getContents(node)
  2126. indx = 0
  2127. num = len(contents)
  2128. #XXX ugly
  2129. if not num:
  2130. return
  2131. component = SplitQName(contents[indx].getTagName())[1]
  2132. if component == 'annotation':
  2133. self.annotation = Annotation(self)
  2134. self.annotation.fromDom(contents[indx])
  2135. indx += 1
  2136. component = SplitQName(contents[indx].getTagName())[1]
  2137. if component == 'all':
  2138. self.content = All(self)
  2139. self.content.fromDom(contents[indx])
  2140. indx += 1
  2141. elif component == 'choice':
  2142. self.content = Choice(self)
  2143. self.content.fromDom(contents[indx])
  2144. indx += 1
  2145. elif component == 'sequence':
  2146. self.content = Sequence(self)
  2147. self.content.fromDom(contents[indx])
  2148. indx += 1
  2149. elif component == 'group':
  2150. self.content = ModelGroupReference(self)
  2151. self.content.fromDom(contents[indx])
  2152. indx += 1
  2153. else:
  2154. self.content = None
  2155. self.attr_content = []
  2156. while indx < num:
  2157. component = SplitQName(contents[indx].getTagName())[1]
  2158. if component == 'attribute':
  2159. if contents[indx].hasattr('ref'):
  2160. self.attr_content.append(AttributeReference(self))
  2161. else:
  2162. self.attr_content.append(LocalAttributeDeclaration(self))
  2163. elif component == 'attributeGroup':
  2164. if contents[indx].hasattr('ref'):
  2165. self.attr_content.append(AttributeGroupReference(self))
  2166. else:
  2167. self.attr_content.append(AttributeGroupDefinition(self))
  2168. elif component == 'anyAttribute':
  2169. self.attr_content.append(AttributeWildCard(self))
  2170. else:
  2171. raise SchemaError, 'Unknown component (%s)' %(contents[indx].getTagName())
  2172. self.attr_content[-1].fromDom(contents[indx])
  2173. indx += 1
  2174. class Extension(_DerivationBase,
  2175. ExtensionMarker):
  2176. """<extension base>
  2177. parents:
  2178. complexContent
  2179. attributes:
  2180. id -- ID
  2181. base -- QName, required
  2182. contents:
  2183. annotation?, (group | all | choice | sequence)?,
  2184. (attribute | attributeGroup)*, anyAttribute?
  2185. """
  2186. tag = 'extension'
  2187. class Restriction(_DerivationBase,\
  2188. RestrictionMarker):
  2189. """<restriction base>
  2190. parents:
  2191. complexContent
  2192. attributes:
  2193. id -- ID
  2194. base -- QName, required
  2195. contents:
  2196. annotation?, (group | all | choice | sequence)?,
  2197. (attribute | attributeGroup)*, anyAttribute?
  2198. """
  2199. tag = 'restriction'
  2200. class SimpleContent(_DerivedType,\
  2201. SimpleMarker):
  2202. """<simpleContent>
  2203. parents:
  2204. complexType
  2205. attributes:
  2206. id -- ID
  2207. contents:
  2208. annotation?, (restriction | extension)
  2209. """
  2210. attributes = {'id':None}
  2211. contents = {'xsd':['annotation', 'restriction', 'extension']}
  2212. tag = 'simpleContent'
  2213. class Extension(XMLSchemaComponent,\
  2214. ExtensionMarker):
  2215. """<extension base>
  2216. parents:
  2217. simpleContent
  2218. attributes:
  2219. id -- ID
  2220. base -- QName, required
  2221. contents:
  2222. annotation?, (attribute | attributeGroup)*, anyAttribute?
  2223. """
  2224. required = ['base']
  2225. attributes = {'id':None,
  2226. 'base':None }
  2227. contents = {'xsd':['annotation', 'attribute', 'attributeGroup',
  2228. 'anyAttribute']}
  2229. tag = 'extension'
  2230. def __init__(self, parent):
  2231. XMLSchemaComponent.__init__(self, parent)
  2232. self.annotation = None
  2233. self.attr_content = None
  2234. def getAttributeContent(self):
  2235. return self.attr_content
  2236. def fromDom(self, node):
  2237. self.setAttributes(node)
  2238. contents = self.getContents(node)
  2239. indx = 0
  2240. num = len(contents)
  2241. if num:
  2242. component = SplitQName(contents[indx].getTagName())[1]
  2243. if component == 'annotation':
  2244. self.annotation = Annotation(self)
  2245. self.annotation.fromDom(contents[indx])
  2246. indx += 1
  2247. component = SplitQName(contents[indx].getTagName())[1]
  2248. content = []
  2249. while indx < num:
  2250. component = SplitQName(contents[indx].getTagName())[1]
  2251. if component == 'attribute':
  2252. if contents[indx].hasattr('ref'):
  2253. content.append(AttributeReference(self))
  2254. else:
  2255. content.append(LocalAttributeDeclaration(self))
  2256. elif component == 'attributeGroup':
  2257. content.append(AttributeGroupReference(self))
  2258. elif component == 'anyAttribute':
  2259. content.append(AttributeWildCard(self))
  2260. else:
  2261. raise SchemaError, 'Unknown component (%s)'\
  2262. %(contents[indx].getTagName())
  2263. content[-1].fromDom(contents[indx])
  2264. indx += 1
  2265. self.attr_content = tuple(content)
  2266. class Restriction(XMLSchemaComponent,\
  2267. RestrictionMarker):
  2268. """<restriction base>
  2269. parents:
  2270. simpleContent
  2271. attributes:
  2272. id -- ID
  2273. base -- QName, required
  2274. contents:
  2275. annotation?, simpleType?, (enumeration | length |
  2276. maxExclusive | maxInclusive | maxLength | minExclusive |
  2277. minInclusive | minLength | pattern | fractionDigits |
  2278. totalDigits | whiteSpace)*, (attribute | attributeGroup)*,
  2279. anyAttribute?
  2280. """
  2281. required = ['base']
  2282. attributes = {'id':None,
  2283. 'base':None }
  2284. contents = {'xsd':['annotation', 'simpleType', 'attribute',\
  2285. 'attributeGroup', 'anyAttribute'] + RestrictionMarker.facets}
  2286. tag = 'restriction'
  2287. def __init__(self, parent):
  2288. XMLSchemaComponent.__init__(self, parent)
  2289. self.annotation = None
  2290. self.content = None
  2291. self.attr_content = None
  2292. def getAttributeContent(self):
  2293. return self.attr_content
  2294. def fromDom(self, node):
  2295. self.content = []
  2296. self.setAttributes(node)
  2297. contents = self.getContents(node)
  2298. indx = 0
  2299. num = len(contents)
  2300. component = SplitQName(contents[indx].getTagName())[1]
  2301. if component == 'annotation':
  2302. self.annotation = Annotation(self)
  2303. self.annotation.fromDom(contents[indx])
  2304. indx += 1
  2305. component = SplitQName(contents[indx].getTagName())[1]
  2306. content = []
  2307. while indx < num:
  2308. component = SplitQName(contents[indx].getTagName())[1]
  2309. if component == 'attribute':
  2310. if contents[indx].hasattr('ref'):
  2311. content.append(AttributeReference(self))
  2312. else:
  2313. content.append(LocalAttributeDeclaration(self))
  2314. elif component == 'attributeGroup':
  2315. content.append(AttributeGroupReference(self))
  2316. elif component == 'anyAttribute':
  2317. content.append(AttributeWildCard(self))
  2318. elif component == 'simpleType':
  2319. self.content.append(LocalSimpleType(self))
  2320. self.content[-1].fromDom(contents[indx])
  2321. else:
  2322. raise SchemaError, 'Unknown component (%s)'\
  2323. %(contents[indx].getTagName())
  2324. content[-1].fromDom(contents[indx])
  2325. indx += 1
  2326. self.attr_content = tuple(content)
  2327. class LocalComplexType(ComplexType,\
  2328. LocalMarker):
  2329. """<complexType>
  2330. parents:
  2331. element
  2332. attributes:
  2333. id -- ID
  2334. mixed -- boolean, false
  2335. contents:
  2336. annotation?, (simpleContent | complexContent |
  2337. ((group | all | choice | sequence)?, (attribute | attributeGroup)*, anyAttribute?))
  2338. """
  2339. required = []
  2340. attributes = {'id':None,
  2341. 'mixed':0}
  2342. tag = 'complexType'
  2343. class SimpleType(XMLSchemaComponent,\
  2344. DefinitionMarker,\
  2345. SimpleMarker):
  2346. """<simpleType name>
  2347. parents:
  2348. redefine, schema
  2349. attributes:
  2350. id -- ID
  2351. name -- NCName, required
  2352. final -- ('#all' | ('extension' | 'restriction' | 'list' | 'union')*),
  2353. schema.finalDefault
  2354. contents:
  2355. annotation?, (restriction | list | union)
  2356. """
  2357. required = ['name']
  2358. attributes = {'id':None,
  2359. 'name':None,
  2360. 'final':lambda self: self._parent().getFinalDefault()}
  2361. contents = {'xsd':['annotation', 'restriction', 'list', 'union']}
  2362. tag = 'simpleType'
  2363. def __init__(self, parent):
  2364. XMLSchemaComponent.__init__(self, parent)
  2365. self.annotation = None
  2366. self.content = None
  2367. def getElementDeclaration(self, attribute):
  2368. raise Warning, 'invalid operation for <%s>' %self.tag
  2369. def getTypeDefinition(self, attribute):
  2370. raise Warning, 'invalid operation for <%s>' %self.tag
  2371. def fromDom(self, node):
  2372. self.setAttributes(node)
  2373. contents = self.getContents(node)
  2374. for child in contents:
  2375. component = SplitQName(child.getTagName())[1]
  2376. if component == 'annotation':
  2377. self.annotation = Annotation(self)
  2378. self.annotation.fromDom(child)
  2379. continue
  2380. break
  2381. else:
  2382. return
  2383. if component == 'restriction':
  2384. self.content = self.__class__.Restriction(self)
  2385. elif component == 'list':
  2386. self.content = self.__class__.List(self)
  2387. elif component == 'union':
  2388. self.content = self.__class__.Union(self)
  2389. else:
  2390. raise SchemaError, 'Unknown component (%s)' %(component)
  2391. self.content.fromDom(child)
  2392. class Restriction(XMLSchemaComponent,\
  2393. RestrictionMarker):
  2394. """<restriction base>
  2395. parents:
  2396. simpleType
  2397. attributes:
  2398. id -- ID
  2399. base -- QName, required or simpleType child
  2400. contents:
  2401. annotation?, simpleType?, (enumeration | length |
  2402. maxExclusive | maxInclusive | maxLength | minExclusive |
  2403. minInclusive | minLength | pattern | fractionDigits |
  2404. totalDigits | whiteSpace)*
  2405. """
  2406. attributes = {'id':None,
  2407. 'base':None }
  2408. contents = {'xsd':['annotation', 'simpleType']+RestrictionMarker.facets}
  2409. tag = 'restriction'
  2410. def __init__(self, parent):
  2411. XMLSchemaComponent.__init__(self, parent)
  2412. self.annotation = None
  2413. self.content = None
  2414. def getAttributeBase(self):
  2415. return XMLSchemaComponent.getAttribute(self, 'base')
  2416. def getTypeDefinition(self, attribute='base'):
  2417. return XMLSchemaComponent.getTypeDefinition(self, attribute)
  2418. def getSimpleTypeContent(self):
  2419. for el in self.content:
  2420. if el.isSimple(): return el
  2421. return None
  2422. def fromDom(self, node):
  2423. self.setAttributes(node)
  2424. contents = self.getContents(node)
  2425. content = []
  2426. for indx in range(len(contents)):
  2427. component = SplitQName(contents[indx].getTagName())[1]
  2428. if (component == 'annotation') and (not indx):
  2429. self.annotation = Annotation(self)
  2430. self.annotation.fromDom(contents[indx])
  2431. continue
  2432. elif (component == 'simpleType') and (not indx or indx == 1):
  2433. content.append(AnonymousSimpleType(self))
  2434. content[-1].fromDom(contents[indx])
  2435. elif component in RestrictionMarker.facets:
  2436. #print_debug('%s class instance, skipping %s' %(self.__class__, component))
  2437. pass
  2438. else:
  2439. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  2440. self.content = tuple(content)
  2441. class Union(XMLSchemaComponent,
  2442. UnionMarker):
  2443. """<union>
  2444. parents:
  2445. simpleType
  2446. attributes:
  2447. id -- ID
  2448. memberTypes -- list of QNames, required or simpleType child.
  2449. contents:
  2450. annotation?, simpleType*
  2451. """
  2452. attributes = {'id':None,
  2453. 'memberTypes':None }
  2454. contents = {'xsd':['annotation', 'simpleType']}
  2455. tag = 'union'
  2456. def __init__(self, parent):
  2457. XMLSchemaComponent.__init__(self, parent)
  2458. self.annotation = None
  2459. self.content = None
  2460. def fromDom(self, node):
  2461. self.setAttributes(node)
  2462. contents = self.getContents(node)
  2463. content = []
  2464. for indx in range(len(contents)):
  2465. component = SplitQName(contents[indx].getTagName())[1]
  2466. if (component == 'annotation') and (not indx):
  2467. self.annotation = Annotation(self)
  2468. self.annotation.fromDom(contents[indx])
  2469. elif (component == 'simpleType'):
  2470. content.append(AnonymousSimpleType(self))
  2471. content[-1].fromDom(contents[indx])
  2472. else:
  2473. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  2474. self.content = tuple(content)
  2475. class List(XMLSchemaComponent,
  2476. ListMarker):
  2477. """<list>
  2478. parents:
  2479. simpleType
  2480. attributes:
  2481. id -- ID
  2482. itemType -- QName, required or simpleType child.
  2483. contents:
  2484. annotation?, simpleType?
  2485. """
  2486. attributes = {'id':None,
  2487. 'itemType':None }
  2488. contents = {'xsd':['annotation', 'simpleType']}
  2489. tag = 'list'
  2490. def __init__(self, parent):
  2491. XMLSchemaComponent.__init__(self, parent)
  2492. self.annotation = None
  2493. self.content = None
  2494. def getItemType(self):
  2495. return self.attributes.get('itemType')
  2496. def getTypeDefinition(self, attribute='itemType'):
  2497. """
  2498. return the type refered to by itemType attribute or
  2499. the simpleType content. If returns None, then the
  2500. type refered to by itemType is primitive.
  2501. """
  2502. tp = XMLSchemaComponent.getTypeDefinition(self, attribute)
  2503. return tp or self.content
  2504. def fromDom(self, node):
  2505. self.annotation = None
  2506. self.content = None
  2507. self.setAttributes(node)
  2508. contents = self.getContents(node)
  2509. for indx in range(len(contents)):
  2510. component = SplitQName(contents[indx].getTagName())[1]
  2511. if (component == 'annotation') and (not indx):
  2512. self.annotation = Annotation(self)
  2513. self.annotation.fromDom(contents[indx])
  2514. elif (component == 'simpleType'):
  2515. self.content = AnonymousSimpleType(self)
  2516. self.content.fromDom(contents[indx])
  2517. break
  2518. else:
  2519. raise SchemaError, 'Unknown component (%s)' %(i.getTagName())
  2520. class AnonymousSimpleType(SimpleType,\
  2521. SimpleMarker,\
  2522. LocalMarker):
  2523. """<simpleType>
  2524. parents:
  2525. attribute, element, list, restriction, union
  2526. attributes:
  2527. id -- ID
  2528. contents:
  2529. annotation?, (restriction | list | union)
  2530. """
  2531. required = []
  2532. attributes = {'id':None}
  2533. tag = 'simpleType'
  2534. class Redefine:
  2535. """<redefine>
  2536. parents:
  2537. attributes:
  2538. contents:
  2539. """
  2540. tag = 'redefine'
  2541. ###########################
  2542. ###########################
  2543. if sys.version_info[:2] >= (2, 2):
  2544. tupleClass = tuple
  2545. else:
  2546. import UserTuple
  2547. tupleClass = UserTuple.UserTuple
  2548. class TypeDescriptionComponent(tupleClass):
  2549. """Tuple of length 2, consisting of
  2550. a namespace and unprefixed name.
  2551. """
  2552. def __init__(self, args):
  2553. """args -- (namespace, name)
  2554. Remove the name's prefix, irrelevant.
  2555. """
  2556. if len(args) != 2:
  2557. raise TypeError, 'expecting tuple (namespace, name), got %s' %args
  2558. elif args[1].find(':') >= 0:
  2559. args = (args[0], SplitQName(args[1])[1])
  2560. tuple.__init__(self, args)
  2561. return
  2562. def getTargetNamespace(self):
  2563. return self[0]
  2564. def getName(self):
  2565. return self[1]