1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 """This module contains support classes from which schema-specific bindings
17 inherit, and that describe the content models of those schema."""
18
19 import logging
20 import pyxb
21 import xml.dom
22 import pyxb.utils.domutils as domutils
23 import pyxb.utils.utility as utility
24 import types
25 import pyxb.namespace
26 from pyxb.namespace.builtin import XMLSchema_instance as XSI
27
28 _log = logging.getLogger(__name__)
31
32 @classmethod
43
44 _ExpandedName = None
45 """The expanded name of the component."""
46
47 _DefinitionLocation = None
48 """Where the definition can be found in the originating schema."""
49
50 _ReservedSymbols = set([ 'validateBinding', 'toDOM', 'toxml', 'Factory', 'property' ])
51
52 if pyxb._CorruptionDetectionEnabled:
57
58 _PyXBFactoryKeywords = ( '_dom_node', '_fallback_namespace', '_from_xml',
59 '_apply_whitespace_facet', '_validate_constraints',
60 '_require_value', '_nil', '_element',
61 '_convert_string_values' )
62 """Keywords that are interpreted by __new__ or __init__ in one or more
63 classes in the PyXB type hierarchy. All these keywords must be removed
64 before invoking base Python __init__ or __new__."""
65
66
67
68
69 _Abstract = False
70
72 """Return a L{namespace context <pyxb.binding.NamespaceContext>}
73 associated with the binding instance.
74
75 This will return C{None} unless something has provided a context to
76 the instance. Context is provided when instances are generated by the
77 DOM and SAX-based translators."""
78 return self.__namespaceContext
79 - def _setNamespaceContext (self, namespace_context):
80 """Associate a L{namespace context <pyxb.binding.NamespaceContext>}
81 with the binding instance."""
82 self.__namespaceContext = namespace_context
83 return self
84 __namespaceContext = None
85
87 """Associate a L{pyxb.binding.basis.element} with the instance."""
88 self.__element = element
89 return self
91 """Return a L{pyxb.binding.basis.element} associated with the binding
92 instance.
93
94 This will return C{None} unless an element has been associated.
95 Constructing a binding instance using the element instance will add
96 this association.
97 """
98 return self.__element
99 __element = None
100
101 __xsiNil = None
103 """Indicate whether this instance is U{nil
104 <http://www.w3.org/TR/xmlschema-1/#xsi_nil>}.
105
106 The value is set by the DOM and SAX parsers when building an instance
107 from a DOM element with U{xsi:nil
108 <http://www.w3.org/TR/xmlschema-1/#xsi_nil>} set to C{true}.
109
110 @return: C{None} if the element used to create the instance is not
111 U{nillable<http://www.w3.org/TR/xmlschema-1/#nillable>}.
112 If it is nillable, returns C{True} or C{False} depending on
113 whether the instance itself is U{nil<http://www.w3.org/TR/xmlschema-1/#xsi_nil>}.
114 """
115 return self.__xsiNil
117 """Set the xsi:nil property of the instance.
118
119 @raise pyxb.NoNillableSupportError: the instance is not associated
120 with an element that is L{nillable
121 <pyxb.binding.basis.element.nillable>}.
122 """
123 if self.__xsiNil is None:
124 raise pyxb.NoNillableSupportError(type(self))
125 self.__xsiNil = True
126 self._resetContent()
127
128 - def _resetContent (self):
130
131 __constructedWithValue = False
145
146
147
148
149 __WarnedUnassociatedElement = False
150
161
162 @classmethod
164 """Method invoked upon entry to the Factory method.
165
166 This method is entitled to modify the keywords array. It can also
167 return a state value which is passed to _postFactory_vx."""
168 return None
169
170 - def _postFactory_vx (cls, state):
171 """Method invoked prior to leaving the Factory method.
172
173 This is an instance method, and is given the state that was returned
174 by _PreFactory_vx."""
175 return None
176
177 @classmethod
179 """Provide a common mechanism to create new instances of this type.
180
181 The class constructor won't do, because you can't create
182 instances of union types.
183
184 This method may be overridden in subclasses (like STD_union). Pre-
185 and post-creation actions can be customized on a per-class instance by
186 overriding the L{_PreFactory_vx} and L{_postFactory_vx} methods.
187
188 @keyword _dom_node: If provided, the value must be a DOM node, the
189 content of which will be used to set the value of the instance.
190
191 @keyword _from_xml: If C{True}, the input must be either a DOM node or
192 a unicode string comprising a lexical representation of a value. This
193 is a further control on C{_apply_whitespace_facet} and arises from
194 cases where the lexical and value representations cannot be
195 distinguished by type. The default value is C{True} iff C{_dom_node}
196 is not C{None}.
197
198 @keyword _apply_whitespace_facet: If C{True} and this is a
199 simpleTypeDefinition with a whiteSpace facet, the first argument will
200 be normalized in accordance with that facet prior to invoking the
201 parent constructor.
202
203 @keyword _validate_constraints: If C{True}, any constructed value is
204 checked against constraints applied to the union as well as the member
205 type.
206
207 @keyword _require_value: If C{False} (default), it is permitted to
208 create a value without an initial value. If C{True} and no initial
209 value was provided, causes L{pyxb.MissingContentError} to be raised.
210 Only applies to simpleTypeDefinition instances; this is used when
211 creating values from DOM nodes.
212 """
213
214
215 dom_node = kw.get('_dom_node')
216 kw.setdefault('_from_xml', dom_node is not None)
217 used_cls = cls._SupersedingClass()
218 state = used_cls._PreFactory_vx(args, kw)
219 rv = cls._DynamicCreate(*args, **kw)
220 rv._postFactory_vx(state)
221 if isinstance(dom_node, utility.Locatable_mixin):
222 rv._setLocation(dom_node.location)
223 return rv
224
229
230 @classmethod
232 """Return C{True} iff this is the ur-type.
233
234 The only ur-type is {http://www.w3.org/2001/XMLSchema}anyType. The
235 implementation of this method is overridden for
236 L{pyxb.binding.datatypes.anyType}."""
237 return False
238
239 @classmethod
245
246 @classmethod
248 """Return a variant of the value that is compatible with this type.
249
250 Compatibility is defined relative to the type definition associated
251 with the element. The value C{None} is always compatible. If
252 C{value} has a Python type (e.g., C{int}) that is a superclass of the
253 required L{_TypeBinding_mixin} class (e.g., C{xs:byte}), C{value} is
254 used as a constructor parameter to return a new instance of the
255 required type. Note that constraining facets are applied here if
256 necessary (e.g., although a Python C{int} with value C{500} is
257 type-compatible with C{xs:byte}, it is outside the value space, and
258 compatibility will fail).
259
260 @keyword _convert_string_values: If C{True} (default) and the incoming value is
261 a string, an attempt will be made to form a compatible value by using
262 the string as a constructor argument to the this class. This flag is
263 set to C{False} when testing automaton transitions.
264
265 @raise pyxb.BadTypeValueError: if the value is not both
266 type-consistent and value-consistent with the element's type.
267 """
268 convert_string_values = kw.get('_convert_string_values', True)
269
270 if value is None:
271 return None
272
273 if isinstance(value, cls):
274
275
276 return value
277 value_type = type(value)
278
279 if str == value_type:
280 value_type = unicode
281
282
283
284 if issubclass(cls, value_type):
285 return cls(value)
286
287
288
289 if isinstance(value, int) and issubclass(cls, long):
290 return cls(value)
291
292
293 if isinstance(value, bool) and issubclass(cls, pyxb.binding.datatypes.boolean):
294 return cls(value)
295
296
297
298 if convert_string_values and (unicode == value_type):
299 return cls(value)
300
301
302 if issubclass(cls, STD_union):
303 for mt in cls._MemberTypes:
304 try:
305 return mt._CompatibleValue(value, **kw)
306 except:
307 pass
308
309
310 if (pyxb.binding.datatypes.anySimpleType == cls) and issubclass(value_type, simpleTypeDefinition):
311 return value
312 if pyxb.binding.datatypes.anyType == cls:
313 if not isinstance(value, _TypeBinding_mixin):
314 _log.info('Created %s instance from value of type %s', cls._ExpandedName, type(value))
315 value = cls(value)
316 return value
317
318
319
320 if isinstance(value, pyxb.BIND):
321 return value.createInstance(cls.Factory, **kw)
322
323
324
325
326
327
328 raise pyxb.BadTypeValueError('No conversion from %s to %s' % (value_type, cls))
329
330 @classmethod
332 """Return True iff the content of this binding object is a simple type.
333
334 This is true only for descendents of simpleTypeDefinition and instances
335 of complexTypeDefinition that have simple type content."""
336 raise pyxb.LogicError('Failed to override _TypeBinding_mixin._IsSimpleTypeContent')
337
338
339
340
341 _AttributeWildcard = None
342
343 _AttributeMap = { }
344 """Map from expanded names to AttributeUse instances. Non-empty only in
345 L{complexTypeDefinition} subclasses."""
346
347 @classmethod
367
369 """Invoke self._setAttribute based on node attributes and keywords.
370
371 Though attributes can only legally appear in complexTypeDefinition
372 instances, delayed conditional validation requires caching them in
373 simpleTypeDefinition.
374
375 @param kw: keywords passed to the constructor. This map is mutated by
376 the call: keywords corresponding to recognized attributes are removed.
377
378 @param dom_node: an xml.dom Node instance, possibly C{None}
379 """
380
381
382 attribute_settings = { }
383 if dom_node is not None:
384 attribute_settings.update(self.__AttributesFromDOM(dom_node))
385 for fu in self._AttributeMap.values():
386 iv = kw.pop(fu.id(), None)
387 if iv is not None:
388 attribute_settings[fu.name()] = iv
389 for (attr_en, value) in attribute_settings.items():
390 self._setAttribute(attr_en, value)
391
392 - def toDOM (self, bds=None, parent=None, element_name=None):
393 """Convert this instance to a DOM node.
394
395 The name of the top-level element is either the name of the L{element}
396 instance associated with this instance, or the XML name of the type of
397 this instance.
398
399 @param bds: Support for customizing the generated document
400 @type bds: L{pyxb.utils.domutils.BindingDOMSupport}
401 @param parent: If C{None}, a standalone document is created;
402 otherwise, the created element is a child of the given element.
403 @type parent: C{xml.dom.Element} or C{None}
404 @rtype: C{xml.dom.Document}
405 """
406
407 if bds is None:
408 bds = domutils.BindingDOMSupport()
409 need_xsi_type = bds.requireXSIType()
410 if isinstance(element_name, (str, unicode)):
411 element_name = pyxb.namespace.ExpandedName(bds.defaultNamespace(), element_name)
412 if (element_name is None) and (self._element() is not None):
413 element_binding = self._element()
414 element_name = element_binding.name()
415 need_xsi_type = need_xsi_type or element_binding.typeDefinition()._RequireXSIType(type(self))
416 if element_name is None:
417 element_name = self._ExpandedName
418 element = bds.createChildElement(element_name, parent)
419 if need_xsi_type:
420 val_type_qname = self._ExpandedName.localName()
421 tns_prefix = bds.namespacePrefix(self._ExpandedName.namespace())
422 if tns_prefix is not None:
423 val_type_qname = '%s:%s' % (tns_prefix, val_type_qname)
424 bds.addAttribute(element, XSI.type, val_type_qname)
425 self._toDOM_csc(bds, element)
426 bds.finalize()
427 return bds.document()
428
429 - def toxml (self, encoding=None, bds=None, root_only=False):
430 """Shorthand to get the object as an XML document.
431
432 If you want to set the default namespace, pass in a pre-configured
433 C{bds}.
434
435 @param encoding: The encoding to be used. See
436 @C{xml.dom.Node.toxml()} for a description of why you should always
437 pass @C{'utf-8'} here. Because this method follows the contract of
438 the corresponding C{xml.dom.Node} method, it does not automatically
439 get the default PyXB output encoding.
440
441 @param bds: Optional L{pyxb.utils.domutils.BindingDOMSupport} instance
442 to use for creation. If not provided (default), a new generic one is
443 created.
444 """
445 dom = self.toDOM(bds)
446 if root_only:
447 dom = dom.documentElement
448 return dom.toxml(encoding)
449
455
457 """Override in subclasses for type-specific validation of instance
458 content.
459
460 @return: C{True} if the instance validates
461 @raise pyxb.BindingValidationError: complex content does not match model
462 @raise pyxb.BadTypeValueError: simple content fails to satisfy constraints
463 """
464 raise pyxb.IncompleteImplementationError('%s did not override _validateBinding_vx' % (type(self),))
465
467 """Check whether the binding content matches its content model.
468
469 @return: C{True} if validation succeeds.
470 @raise pyxb.BindingValidationError: complex content does not match model
471 @raise pyxb.BadTypeValueError: simple content fails to satisfy constraints
472 """
473 if self._PerformValidation():
474 self._validateBinding_vx()
475 return True
476
477 - def _postDOMValidate (self):
478 self.validateBinding()
479 return self
480
481 @classmethod
488
490 """Helper to allow overriding the implementation class.
491
492 Generally we'll want to augment the generated bindings by subclassing
493 them, and adding functionality to the subclass. This mix-in provides a
494 way to communicate the existence of the superseding subclass back to the
495 binding infrastructure, so that when it creates an instance it uses the
496 subclass rather than the unaugmented binding class.
497
498 When a raw generated binding is subclassed, L{_SetSupersedingClass} should be
499 invoked on the raw class passing in the superseding subclass. E.g.::
500
501 class mywsdl (raw.wsdl):
502 pass
503 raw.wsdl._SetSupersedingClass(mywsdl)
504
505 """
506
507 @classmethod
509 return '_%s__SupersedingClass' % (cls.__name__,)
510
511 @classmethod
513 return '_%s__AlternativeConstructor' % (cls.__name__,)
514
515 @classmethod
519
520 @classmethod
522 """Return the class stored in the class reference attribute."""
523 rv = getattr(cls, cls.__AlternativeConstructorAttribute(), None)
524 if isinstance(rv, tuple):
525 rv = rv[0]
526 return rv
527
528 @classmethod
530 """Set the class reference attribute.
531
532 @param superseding: A Python class that is a subclass of this class.
533 """
534 assert (superseding is None) or issubclass(superseding, cls)
535 if superseding is None:
536 cls.__dict__.pop(cls.__SupersedingClassAttribute(), None)
537 else:
538 setattr(cls, cls.__SupersedingClassAttribute(), superseding)
539 return superseding
540
541 @classmethod
543 attr = cls.__AlternativeConstructorAttribute()
544 if alternative_constructor is None:
545 cls.__dict__.pop(attr, None)
546 else:
547
548
549
550 setattr(cls, attr, (alternative_constructor,))
551 assert cls._AlternativeConstructor() == alternative_constructor
552 return alternative_constructor
553
554 @classmethod
564
565 -class simpleTypeDefinition (_TypeBinding_mixin, utility._DeconflictSymbols_mixin, _DynamicCreate_mixin):
566 """L{simpleTypeDefinition} is a base class that is part of the
567 hierarchy of any class that represents the Python datatype for a
568 L{SimpleTypeDefinition<pyxb.xmlschema.structures.SimpleTypeDefinition>}.
569
570 @note: This class, or a descendent of it, must be the first class
571 in the method resolution order when a subclass has multiple
572 parents. Otherwise, constructor keyword arguments may not be
573 removed before passing them on to Python classes that do not
574 accept them.
575 """
576
577
578
579
580 __FacetMap = {}
581
582 _ReservedSymbols = _TypeBinding_mixin._ReservedSymbols.union(set([ 'XsdLiteral', 'xsdLiteral',
583 'XsdSuperType', 'XsdPythonType', 'XsdConstraintsOK',
584 'xsdConstraintsOK', 'XsdValueLength', 'xsdValueLength',
585 'PythonLiteral', 'pythonLiteral',
586 'SimpleTypeDefinition' ]))
587 """Symbols that remain the responsibility of this class. Any
588 public symbols in generated binding subclasses are deconflicted
589 by providing an alternative name in the subclass. (There
590 currently are no public symbols in generated SimpleTypeDefinion
591 bindings."""
592
593
594
595
596
597 __FacetMapAttributeNameMap = { }
598 @classmethod
600 """ """
601 '''
602 if cls == simpleTypeDefinition:
603 return '_%s__FacetMap' % (cls.__name__.strip('_'),)
604
605 # It is not uncommon for a class in one namespace to extend a class of
606 # the same name in a different namespace, so encode the namespace URI
607 # in the attribute name (if it is part of a namespace).
608 ns_uri = ''
609 try:
610 ns_uri = cls._ExpandedName.namespaceURI()
611 except Exception:
612 pass
613 nm = '_' + utility.MakeIdentifier('%s_%s_FacetMap' % (ns_uri, cls.__name__.strip('_')))
614 '''
615 nm = cls.__FacetMapAttributeNameMap.get(cls)
616 if nm is None:
617 nm = cls.__name__
618 if nm.endswith('_'):
619 nm += '1'
620 if cls == simpleTypeDefinition:
621 nm = '_%s__FacetMap' % (nm,)
622 else:
623
624
625
626 ns_uri = ''
627 try:
628 ns_uri = cls._ExpandedName.namespaceURI()
629 except Exception:
630 pass
631 nm = '_' + utility.MakeIdentifier('%s_%s_FacetMap' % (ns_uri, nm))
632 cls.__FacetMapAttributeNameMap[cls] = nm
633 return nm
634
635 @classmethod
637 """Return a reference to the facet map for this datatype.
638
639 The facet map is a map from leaf facet classes to instances of those
640 classes that constrain or otherwise apply to the lexical or value
641 space of the datatype. Classes may inherit their facet map from their
642 superclass, or may create a new class instance if the class adds a new
643 constraint type.
644
645 :raise AttributeError: if the facet map has not been defined"""
646 return getattr(cls, cls.__FacetMapAttributeName())
647
648 @classmethod
650 """Initialize the facet map for this datatype.
651
652 This must be called exactly once, after all facets belonging to the
653 datatype have been created.
654
655 :raise pyxb.LogicError: if called multiple times (on the same class)
656 :raise pyxb.LogicError: if called when a parent class facet map has not been initialized
657 :return: the facet map"""
658 fm = None
659 try:
660 fm = cls._FacetMap()
661 except AttributeError:
662 pass
663 if fm is not None:
664 raise pyxb.LogicError('%s facet map initialized multiple times: %s' % (cls.__name__, cls.__FacetMapAttributeName()))
665
666
667
668
669
670 source_class = cls
671 while fm is None:
672
673
674 for super_class in source_class.mro():
675 assert super_class is not None
676 if (super_class == simpleTypeDefinition):
677 break
678 if issubclass(super_class, simpleTypeDefinition):
679 try:
680 fm = super_class._FacetMap()
681 break
682 except AttributeError:
683 pass
684 if fm is None:
685 try:
686 source_class = source_class.XsdSuperType()
687 except AttributeError:
688 source_class = None
689 if source_class is None:
690 fm = { }
691 if fm is None:
692 raise pyxb.LogicError('%s is not a child of simpleTypeDefinition' % (cls.__name__,))
693 fm = fm.copy()
694 for facet in args:
695 fm[type(facet)] = facet
696 setattr(cls, cls.__FacetMapAttributeName(), fm)
697 return fm
698
699 @classmethod
702
703 @classmethod
705 """Pre-process the arguments.
706
707 This is used before invoking the parent constructor. One application
708 is to apply the whitespace facet processing; if such a request is in
709 the keywords, it is removed so it does not propagate to the
710 superclass. Another application is to convert the arguments from a
711 string to a list. Binding-specific applications are performed in the
712 overloaded L{_ConvertArguments_vx} method."""
713 dom_node = kw.pop('_dom_node', None)
714 from_xml = kw.get('_from_xml', dom_node is not None)
715 if dom_node is not None:
716 text_content = domutils.ExtractTextContent(dom_node)
717 if text_content is not None:
718 args = (domutils.ExtractTextContent(dom_node),) + args
719 kw['_apply_whitespace_facet'] = True
720 apply_whitespace_facet = kw.pop('_apply_whitespace_facet', from_xml)
721 if (0 < len(args)) and isinstance(args[0], types.StringTypes) and apply_whitespace_facet:
722 cf_whitespace = getattr(cls, '_CF_whiteSpace', None)
723 if cf_whitespace is not None:
724 norm_str = unicode(cf_whitespace.normalizeString(args[0]))
725 args = (norm_str,) + args[1:]
726 kw['_from_xml'] = from_xml
727 return cls._ConvertArguments_vx(args, kw)
728
729
730
731
732
733
734
735
736
737
738
740
741 kw.pop('_validate_constraints', None)
742 kw.pop('_require_value', None)
743 kw.pop('_element', None)
744 kw.pop('_fallback_namespace', None)
745 kw.pop('_nil', None)
746
747 dom_node = kw.get('_dom_node')
748 args = cls._ConvertArguments(args, kw)
749 kw.pop('_from_xml', dom_node is not None)
750 assert issubclass(cls, _TypeBinding_mixin)
751 try:
752 rv = super(simpleTypeDefinition, cls).__new__(cls, *args, **kw)
753 rv._setAttributesFromKeywordsAndDOM(kw, dom_node)
754 return rv
755 except ValueError, e:
756 raise pyxb.BadTypeValueError(e)
757 except OverflowError, e:
758 raise pyxb.BadTypeValueError(e)
759
760
761
763 """Initialize a newly created STD instance.
764
765 Usually there is one positional argument, which is a value that can be
766 converted to the underlying Python type.
767
768 @keyword _validate_constraints: If True (default), the newly
769 constructed value is checked against its constraining facets.
770 @type _validate_constraints: C{bool}
771 """
772
773 validate_constraints = kw.pop('_validate_constraints', self._PerformValidation())
774 require_value = kw.pop('_require_value', False)
775
776
777 args = self._ConvertArguments(args, kw)
778 try:
779 super(simpleTypeDefinition, self).__init__(*args, **kw)
780 except OverflowError, e:
781 raise pyxb.BadTypeValueError(e)
782 if require_value and (not self._constructedWithValue()):
783 raise pyxb.MissingContentError('missing value')
784
785 if validate_constraints:
786 self.xsdConstraintsOK()
787
788
789
790
791
792
793
794 @classmethod
796 return '_%s__SimpleTypeDefinition' % (cls.__name__,)
797
798 @classmethod
800 """Set the L{pyxb.xmlschema.structures.SimpleTypeDefinition} instance
801 associated with this binding."""
802 attr_name = cls.__STDAttrName()
803 if hasattr(cls, attr_name):
804 old_value = getattr(cls, attr_name)
805 if old_value != std:
806 raise pyxb.LogicError('%s: Attempt to override existing STD %s with %s' % (cls, old_value.name(), std.name()))
807 setattr(cls, attr_name, std)
808
809 @classmethod
811 """Return the SimpleTypeDefinition instance for the given
812 class.
813
814 This should only be invoked when generating bindings.
815
816 @raise pyxb.IncompleteImplementationError: no STD instance has been
817 associated with the class.
818
819 """
820 attr_name = cls.__STDAttrName()
821 if hasattr(cls, attr_name):
822 return getattr(cls, attr_name)
823 raise pyxb.IncompleteImplementationError('%s: No STD available' % (cls,))
824
825 @classmethod
827 """Convert from a python value to a string usable in an XML
828 document.
829
830 This should be implemented in the subclass."""
831 raise pyxb.LogicError('%s does not implement XsdLiteral' % (cls,))
832
834 """Return text suitable for representing the value of this
835 instance in an XML document.
836
837 The base class implementation delegates to the object class's
838 XsdLiteral method."""
839 if self._isNil():
840 return ''
841 return self.XsdLiteral(self)
842
843 @classmethod
845 """Find the nearest parent class in the PST hierarchy.
846
847 The value for anySimpleType is None; for all others, it's a
848 primitive or derived PST descendent (including anySimpleType)."""
849 for sc in cls.mro():
850 if sc == cls:
851 continue
852 if simpleTypeDefinition == sc:
853
854
855
856 return cls._XsdBaseType
857 if issubclass(sc, simpleTypeDefinition):
858 return sc
859 raise pyxb.LogicError('No supertype found for %s' % (cls,))
860
861 @classmethod
863 """Pre-extended class method to verify other things before
864 checking constraints.
865
866 This is used for list types, to verify that the values in the
867 list are acceptable, and for token descendents, to check the
868 lexical/value space conformance of the input.
869 """
870 super_fn = getattr(super(simpleTypeDefinition, cls), '_XsdConstraintsPreCheck_vb', lambda *a,**kw: value)
871 return super_fn(value)
872
873
874
875 __ClassFacetSequence = { }
876
877 @classmethod
879 """Validate the given value against the constraints on this class.
880
881 @raise pyxb.BadTypeValueError: if any constraint is violated.
882 """
883
884 value = cls._XsdConstraintsPreCheck_vb(value)
885
886 facet_values = cls.__ClassFacetSequence.get(cls)
887 if facet_values is None:
888
889
890 classes = [ _x for _x in cls.mro() if issubclass(_x, simpleTypeDefinition) ]
891 classes.reverse()
892 cache_result = True
893 facet_values = []
894 for clazz in classes:
895
896
897
898
899
900
901 try:
902 clazz_facets = clazz._FacetMap().values()
903 except AttributeError:
904 cache_result = False
905 clazz_facets = []
906 for v in clazz_facets:
907 if not (v in facet_values):
908 facet_values.append(v)
909 if cache_result:
910 cls.__ClassFacetSequence[cls] = facet_values
911 for f in facet_values:
912 if not f.validateConstraint(value):
913 raise pyxb.BadTypeValueError('%s violation for %s in %s' % (f.Name(), value, cls.__name__))
914 return value
915
917 """Validate the value of this instance against its constraints."""
918 return self.XsdConstraintsOK(self)
919
924
925 @classmethod
927 """Return the length of the given value.
928
929 The length is calculated by a subclass implementation of
930 _XsdValueLength_vx in accordance with
931 http://www.w3.org/TR/xmlschema-2/#rf-length.
932
933 The return value is a non-negative integer, or C{None} if length
934 constraints should be considered trivially satisfied (as with
935 QName and NOTATION).
936
937 :raise pyxb.LogicError: the provided value is not an instance of cls.
938 :raise pyxb.LogicError: an attempt is made to calculate a length for
939 an instance of a type that does not support length calculations.
940 """
941 assert isinstance(value, cls)
942 if not hasattr(cls, '_XsdValueLength_vx'):
943 raise pyxb.LogicError('Class %s does not support length validation' % (cls.__name__,))
944 return cls._XsdValueLength_vx(value)
945
947 """Return the length of this instance within its value space.
948
949 See XsdValueLength."""
950 return self.XsdValueLength(self)
951
952 @classmethod
954 """Return a string which can be embedded into Python source to
955 represent the given value as an instance of this class."""
956 class_name = cls.__name__
957 return '%s(%s)' % (class_name, repr(value))
958
960 """Return a string which can be embedded into Python source to
961 represent the value of this instance."""
962 return self.PythonLiteral(self)
963
968
969 @classmethod
971 """STDs have simple type content."""
972 return True
973
974 @classmethod
982
983 @classmethod
985
986 """NB: Invoking this on a value that is a list will, if necessary,
987 replace the members of the list with new values that are of the
988 correct item type. This is permitted because only with lists is it
989 possible to bypass the normal content validation (by invoking
990 append/extend on the list instance)."""
991 if value is None:
992 raise pyxb.BadTypeValueError('None is not a valid instance of %s' % (cls,))
993 value_class = cls
994 if issubclass(cls, STD_list):
995 try:
996 iter(value)
997 except TypeError:
998 raise pyxb.BadTypeValueError('%s cannot have non-iterable value type %s' % (cls, type(value)))
999 for v in value:
1000 if not cls._ItemType._IsValidValue(v):
1001 raise pyxb.BadTypeValueError('%s cannot have member of type %s (want %s)' % (cls, type(v), cls._ItemType))
1002 else:
1003 if issubclass(cls, STD_union):
1004 value_class = None
1005 for mt in cls._MemberTypes:
1006 if mt._IsValidValue(value):
1007 value_class = mt
1008 break
1009 if value_class is None:
1010 raise pyxb.BadTypeValueError('%s cannot have value type %s' % (cls, type(value)))
1011
1012 if not isinstance(value, value_class):
1013 raise pyxb.BadTypeValueError('Value type %s is not valid for %s' % (type(value), cls))
1014 value_class.XsdConstraintsOK(value)
1015
1018
1021
1024
1025 @classmethod
1026 - def _description (cls, name_only=False, user_documentation=True):
1027 name = cls._Name()
1028 if name_only:
1029 return name
1030 desc = [ name, ' restriction of ', cls.XsdSuperType()._description(name_only=True) ]
1031 if user_documentation and (cls._Documentation is not None):
1032 desc.extend(["\n", cls._Documentation])
1033 return ''.join(desc)
1034
1036 """Base class for union datatypes.
1037
1038 This class descends only from simpleTypeDefinition. A pyxb.LogicError is
1039 raised if an attempt is made to construct an instance of a subclass of
1040 STD_union. Values consistent with the member types are constructed using
1041 the Factory class method. Values are validated using the _ValidatedMember
1042 class method.
1043
1044 Subclasses must provide a class variable _MemberTypes which is a
1045 tuple of legal members of the union."""
1046
1047 _MemberTypes = None
1048 """A list of classes which are permitted as values of the union."""
1049
1050
1051
1052
1053 __FacetMap = {}
1054
1055 @classmethod
1057 """Given a value, attempt to create an instance of some member of this
1058 union. The first instance which can be legally created is returned.
1059
1060 @keyword _validate_constraints: If True (default), any constructed
1061 value is checked against constraints applied to the union as well as
1062 the member type.
1063
1064 @raise pyxb.BadTypeValueError: no member type will permit creation of
1065 an instance from the parameters in C{args} and C{kw}.
1066 """
1067
1068 used_cls = cls._SupersedingClass()
1069 state = used_cls._PreFactory_vx(args, kw)
1070
1071 rv = None
1072
1073 validate_constraints = kw.get('_validate_constraints', cls._PerformValidation())
1074 assert isinstance(validate_constraints, bool)
1075 if 0 < len(args):
1076 arg = args[0]
1077 try:
1078 rv = cls._ValidatedMember(arg)
1079 except pyxb.BadTypeValueError:
1080 pass
1081 if rv is None:
1082 kw['_validate_constraints'] = True
1083 for mt in cls._MemberTypes:
1084 try:
1085 rv = mt.Factory(*args, **kw)
1086 break
1087 except pyxb.BadTypeValueError:
1088 pass
1089 except ValueError:
1090 pass
1091 except:
1092 pass
1093 if rv is not None:
1094 if validate_constraints:
1095 cls.XsdConstraintsOK(rv)
1096 rv._postFactory_vx(state)
1097 return rv
1098 raise pyxb.BadTypeValueError('%s cannot construct union member from args %s' % (cls.__name__, args))
1099
1100 @classmethod
1102 """Validate the given value as a potential union member.
1103
1104 @raise pyxb.BadTypeValueError: the value is not an instance of a
1105 member type."""
1106 if not isinstance(value, cls._MemberTypes):
1107 for mt in cls._MemberTypes:
1108 try:
1109
1110
1111 value = mt.Factory(value, _validate_constraints=True)
1112 return value
1113 except (TypeError, pyxb.BadTypeValueError):
1114 pass
1115 raise pyxb.BadTypeValueError('%s cannot hold a member of type %s' % (cls.__name__, value.__class__.__name__))
1116 return value
1117
1119 raise pyxb.LogicError('%s: cannot construct instances of union' % (self.__class__.__name__,))
1120
1121 @classmethod
1122 - def _description (cls, name_only=False, user_documentation=True):
1129
1130 @classmethod
1134
1135
1136 -class STD_list (simpleTypeDefinition, types.ListType):
1137 """Base class for collection datatypes.
1138
1139 This class descends from the Python list type, and incorporates
1140 simpleTypeDefinition. Subclasses must define a class variable _ItemType
1141 which is a reference to the class of which members must be instances."""
1142
1143 _ItemType = None
1144 """A reference to the binding class for items within this list."""
1145
1146
1147
1148 __FacetMap = {}
1149
1150 @classmethod
1168
1169 @classmethod
1171
1172
1173 if 0 < len(args):
1174 arg1 = args[0]
1175 if isinstance(arg1, types.StringTypes):
1176 args = (arg1.split(),) + args[1:]
1177 arg1 = args[0]
1178 is_iterable = False
1179 try:
1180 iter(arg1)
1181 is_iterable = True
1182 except TypeError:
1183 pass
1184 if is_iterable:
1185 new_arg1 = []
1186 for i in range(len(arg1)):
1187 new_arg1.append(cls._ValidatedItem(arg1[i]))
1188 args = (new_arg1,) + args[1:]
1189 super_fn = getattr(super(STD_list, cls), '_ConvertArguments_vx', lambda *a,**kw: args)
1190 return super_fn(args, kw)
1191
1192 @classmethod
1195
1196 @classmethod
1198 """Convert from a binding value to a string usable in an XML document."""
1199 return ' '.join([ cls._ItemType.XsdLiteral(_v) for _v in value ])
1200
1201 @classmethod
1202 - def _description (cls, name_only=False, user_documentation=True):
1208
1209
1210 @classmethod
1213
1214
1217
1223
1226
1229
1230
1231
1234
1235 - def extend (self, x, _from_xml=False):
1237
1240
1241 - def index (self, x, *args):
1243
1246
1249
1250 -class element (utility._DeconflictSymbols_mixin, _DynamicCreate_mixin):
1251 """Class that represents a schema element.
1252
1253 Global and local elements are represented by instances of this class.
1254 """
1255
1257 """The expanded name of the element within its scope."""
1258 return self.__name
1259 __name = None
1260
1264 __typeDefinition = None
1265
1267 """The scope of the element. This is either C{None}, representing a
1268 top-level element, or an instance of C{complexTypeDefinition} for
1269 local elements."""
1270 return self.__scope
1271 __scope = None
1272
1274 """Indicate whether values matching this element can have U{nil
1275 <http://www.w3.org/TR/xmlschema-1/#xsi_nil>} set."""
1276 return self.__nillable
1277 __nillable = False
1278
1280 """Indicate whether this element is abstract (must use substitution
1281 group members for matches)."""
1282 return self.__abstract
1283 __abstract = False
1284
1286 """Contents of any documentation annotation in the definition."""
1287 return self.__documentation
1288 __documentation = None
1289
1292 __defaultValue = None
1293
1295 """The L{element} instance to whose substitution group this element
1296 belongs. C{None} if this element is not part of a substitution
1297 group."""
1298 return self.__substitutionGroup
1304 __substitutionGroup = None
1305
1313
1315 """Determine whether an instance of this element can substitute for the other element.
1316
1317 See U{Substitution Group OK<http://www.w3.org/TR/xmlschema-1/#cos-equiv-derived-ok-rec>)}.
1318
1319 @todo: Do something about blocking constraints. This ignores them, as
1320 does everything leading to this point.
1321 """
1322 if self.substitutionGroup() is None:
1323 return False
1324 if other is None:
1325 return False
1326 assert isinstance(other, element)
1327
1328
1329 if other.scope() is not None:
1330 other = other.name().elementBinding()
1331 if other is None:
1332 return False
1333 assert other.scope() is None
1334
1335 if self.name().elementBinding() == other:
1336 return True
1337 return (self.substitutionGroup() == other) or self.substitutionGroup().substitutesFor(other)
1338
1340 """Stub replaced by _real_substitutesFor when element supports substitution groups."""
1341 return False
1342
1344 """Return a reference to the element instance used for the given name
1345 within this element.
1346
1347 The type for this element must be a complex type definition."""
1348 return self.typeDefinition()._UseForTag(name).elementBinding()
1349
1350 - def __init__ (self, name, type_definition, scope=None, nillable=False, abstract=False, default_value=None, substitution_group=None, documentation=None):
1363
1365 """Invoke the Factory method on the type associated with this element.
1366
1367 @keyword _dom_node: If set, specifies a DOM node that should be used
1368 for initialization. In that case, the L{createFromDOM} method is
1369 invoked instead of the type definition Factory method.
1370
1371 @note: Other keywords are passed to L{_TypeBinding_mixin.Factory}.
1372
1373 @raise pyxb.AbstractElementError: This element is abstract and no DOM
1374 node was provided.
1375 """
1376 dom_node = kw.pop('_dom_node', None)
1377 assert dom_node is None, 'Cannot pass DOM node directly to element constructor; use createFromDOM'
1378 if '_element' in kw:
1379 raise pyxb.LogicError('Cannot set _element in element-based instance creation')
1380 kw['_element'] = self
1381
1382 if self.abstract():
1383 raise pyxb.AbstractElementError(self)
1384 return self.typeDefinition().Factory(*args, **kw)
1385
1407
1408
1409 @classmethod
1421
1423 """Return the element that should be used if this element binding is
1424 permitted and an element with the given name is encountered.
1425
1426 Normally, the incoming name matches the name of this binding, and
1427 C{self} is returned. If the incoming name is different, it is
1428 expected to be the name of a global element which is within this
1429 element's substitution group. In that case, the binding corresponding
1430 to the named element is return.
1431
1432 @return: An instance of L{element}, or C{None} if no element with the
1433 given name can be found.
1434 """
1435
1436
1437 if self.name() == name:
1438 return self
1439
1440
1441 top_elt = self.name().elementBinding()
1442 if top_elt is None:
1443 return None
1444
1445
1446
1447
1448 elt_en = top_elt.name().adoptName(name)
1449 assert 'elementBinding' in elt_en.namespace()._categoryMap(), 'No element bindings in %s' % (elt_en.namespace(),)
1450 named_elt = elt_en.elementBinding()
1451 if (named_elt is None) or (named_elt == top_elt):
1452 return None
1453 if named_elt.substitutesFor(top_elt):
1454 return named_elt
1455 return None
1456
1457 - def createFromDOM (self, node, expanded_name=None, fallback_namespace=None, **kw):
1458 """Create a binding instance from the given DOM node.
1459
1460 @keyword expanded_name: Optional name for the DOM node. If not
1461 present, is inferred from C{node}.
1462
1463 @keyword fallback_namespace: Optional namespace to use when resolving
1464 unqualified names.
1465 """
1466 if xml.dom.Node.DOCUMENT_NODE == node.nodeType:
1467 node = node.documentElement
1468 if expanded_name is None:
1469 expanded_name = pyxb.namespace.ExpandedName(node, fallback_namespace=fallback_namespace)
1470 return self._createFromDOM(node, expanded_name, **kw)
1471
1473 """Create a binding instance from the given DOM node, using the
1474 provided name to identify the correct binding.
1475
1476 The context and information associated with this element is used to
1477 identify the actual element binding to use. By default, C{self} is
1478 used. If this element represents a term in a content model, the name
1479 and namespace of the incoming node may identify a different element.
1480 If that element is a member of this element's substitution group, the
1481 binding associated with the node's name will be used instead.
1482
1483 The type of object returned is determined by the type definition
1484 associated with the element binding and the value of any U{xsi:type
1485 <http://www.w3.org/TR/xmlschema-1/#xsi_type>} attribute found in the
1486 node, modulated by the configuration of L{XSI.ProcessTypeAttribute<pyxb.namespace.builtin._XMLSchema_instance.ProcessTypeAttribute>}.
1487
1488 Keyword parameters are passed to the factory method of the type
1489 associated with the selected element binding. See
1490 L{_TypeBinding_mixin} and any specializations of it.
1491
1492 @param expanded_name: The expanded name of the node. If the value is
1493 C{None}, defaults to the name of this element. (In the case of
1494 substitution groups, the default is wrong, but correct inference
1495 depends on context not available here.)
1496
1497 @keyword _fallback_namespace: Optional namespace to use when resolving
1498 unqualified type names.
1499
1500 @param node: The DOM node specifying the element content. If this is
1501 a (top-level) Document node, its element node is used.
1502 @type node: C{xml.dom.Node}
1503 @return: An instance of L{_TypeBinding_mixin}
1504 @raise pyxb.StructuralBadDocumentError: The node's name does identify an element binding.
1505 @raise pyxb.AbstractElementError: The element binding associated with the node is abstract.
1506 @raise pyxb.BadDocumentError: An U{xsi:type <http://www.w3.org/TR/xmlschema-1/#xsi_type>} attribute in the node fails to resolve to a recognized type
1507 @raise pyxb.BadDocumentError: An U{xsi:type <http://www.w3.org/TR/xmlschema-1/#xsi_type>} attribute in the node resolves to a type that is not a subclass of the type of the element binding.
1508 """
1509
1510
1511
1512 if xml.dom.Node.DOCUMENT_NODE == node.nodeType:
1513 node = node.documentElement
1514
1515
1516
1517
1518
1519 fallback_namespace = kw.pop('_fallback_namespace', None)
1520 element_binding = self.elementForName(expanded_name)
1521 if element_binding is None:
1522 raise pyxb.StructuralBadDocumentError('Element %s cannot create from node %s' % (self.name(), expanded_name))
1523
1524
1525
1526
1527 if element_binding.abstract():
1528 raise pyxb.AbstractElementError(element_binding)
1529
1530
1531
1532 if '_element' in kw:
1533 raise pyxb.LogicError('Cannot set _element in element-based instance creation')
1534 kw['_element'] = element_binding
1535
1536
1537
1538 type_class = element_binding.typeDefinition()
1539
1540
1541
1542
1543
1544 ns_ctx = pyxb.namespace.resolution.NamespaceContext.GetNodeContext(node)
1545 (did_replace, type_class) = XSI._InterpretTypeAttribute(XSI.type.getAttribute(node), ns_ctx, fallback_namespace, type_class)
1546
1547
1548
1549
1550 is_nil = XSI.nil.getAttribute(node)
1551 if is_nil is not None:
1552 kw['_nil'] = pyxb.binding.datatypes.boolean(is_nil)
1553
1554 rv = type_class.Factory(_dom_node=node, _fallback_namespace=fallback_namespace, **kw)
1555 assert rv._element() == element_binding
1556 rv._setNamespaceContext(ns_ctx)
1557 return rv._postDOMValidate()
1558
1560 return 'Element %s' % (self.name(),)
1561
1562 - def _description (self, name_only=False, user_documentation=True):
1576
1578 """Marker in case we need to know that a PST has an enumeration constraint facet."""
1579
1580 @classmethod
1582 """Return a list of values that the enumeration can take."""
1583 return cls._CF_enumeration.values()
1584
1585 @classmethod
1589
1590 @classmethod
1592 """Return the associated L{pyxb.binding.facet._EnumerationElement} instances."""
1593 return cls._CF_enumeration.items()
1594
1595 @classmethod
1597 """Generate the associated L{pyxb.binding.facet._EnumerationElement} instances."""
1598 return cls._CF_enumeration.iteritems()
1599
1600 -class complexTypeDefinition (_TypeBinding_mixin, utility._DeconflictSymbols_mixin, _DynamicCreate_mixin):
1601 """Base for any Python class that serves as the binding for an
1602 XMLSchema complexType.
1603
1604 Subclasses should define a class-level _AttributeMap variable which maps
1605 from the unicode tag of an attribute to the AttributeUse instance that
1606 defines it. Similarly, subclasses should define an _ElementMap variable.
1607 """
1608
1609 _CT_EMPTY = 'EMPTY'
1610 _CT_SIMPLE = 'SIMPLE'
1611 _CT_MIXED = 'MIXED'
1612 _CT_ELEMENT_ONLY = 'ELEMENT_ONLY'
1613
1614 _ContentTypeTag = None
1615
1616 _TypeDefinition = None
1617 """Subclass of simpleTypeDefinition that corresponds to the type content.
1618 Only valid if _ContentTypeTag is _CT_SIMPLE"""
1619
1620
1621
1622 _HasWildcardElement = False
1623
1624
1625 _ElementMap = { }
1626 """Map from expanded names to ElementUse instances."""
1627
1628
1629
1630 __wildcardAttributeMap = None
1631
1633 """Obtain access to wildcard attributes.
1634
1635 The return value is C{None} if this type does not support wildcard
1636 attributes. If wildcard attributes are allowed, the return value is a
1637 map from QNames to the unicode string value of the corresponding
1638 attribute.
1639
1640 @todo: The map keys should be namespace extended names rather than
1641 QNames, as the in-scope namespace may not be readily available to the
1642 user.
1643 """
1644 return self.__wildcardAttributeMap
1645
1646
1647
1648 __wildcardElements = None
1649
1651 """Obtain access to wildcard elements.
1652
1653 The return value is C{None} if the content model for this type does not
1654 support wildcard elements. If wildcard elements are allowed, the
1655 return value is a list of values corresponding to conformant
1656 unrecognized elements, in the order in which they were encountered.
1657 If the containing binding was created from an XML document and enough
1658 information was present to determine the binding of the member
1659 element, the value is a binding instance. Otherwise, the value is the
1660 original DOM Element node.
1661 """
1662 return self.__wildcardElements
1663
1665 """Create a new instance of this binding.
1666
1667 Arguments are used as transition values along the content model.
1668 Keywords are passed to the constructor of any simple content, or used
1669 to initialize attribute and element values whose L{id
1670 <content.ElementUse.id>} (not L{name <content.ElementUse.name>})
1671 matches the keyword.
1672
1673 @keyword _dom_node: The node to use as the source of binding content.
1674 @type _dom_node: C{xml.dom.Element}
1675
1676 @keyword _from_xml: See L{_TypeBinding_mixin.Factory}
1677
1678 """
1679
1680 fallback_namespace = kw.pop('_fallback_namespace', None)
1681 is_nil = False
1682 dom_node = kw.pop('_dom_node', None)
1683 from_xml = kw.pop('_from_xml', dom_node is not None)
1684 if dom_node is not None:
1685 if isinstance(dom_node, pyxb.utils.utility.Locatable_mixin):
1686 self._setLocation(dom_node.location)
1687 if xml.dom.Node.DOCUMENT_NODE == dom_node.nodeType:
1688 dom_node = dom_node.documentElement
1689
1690 is_nil = XSI.nil.getAttribute(dom_node)
1691 if is_nil is not None:
1692 is_nil = kw['_nil'] = pyxb.binding.datatypes.boolean(is_nil)
1693 if self._AttributeWildcard is not None:
1694 self.__wildcardAttributeMap = { }
1695 if self._HasWildcardElement:
1696 self.__wildcardElements = []
1697 if self._Abstract:
1698 raise pyxb.AbstractInstantiationError(type(self))
1699 super(complexTypeDefinition, self).__init__(**kw)
1700 self.reset()
1701 self._setAttributesFromKeywordsAndDOM(kw, dom_node)
1702 for fu in self._ElementMap.values():
1703 iv = kw.pop(fu.id(), None)
1704 if iv is not None:
1705 fu.set(self, iv)
1706 if kw and kw.pop('_strict_keywords', True):
1707 [ kw.pop(_fkw, None) for _fkw in self._PyXBFactoryKeywords ]
1708 if kw:
1709 raise pyxb.ExtraContentError(kw)
1710 if dom_node is not None:
1711 if self._CT_SIMPLE == self._ContentTypeTag:
1712 self.__initializeSimpleContent(args, dom_node)
1713 else:
1714 self._setContentFromDOM(dom_node, fallback_namespace)
1715 elif 0 < len(args):
1716 self.extend(args, _from_xml=from_xml)
1717 else:
1718 if self._CT_SIMPLE == self._ContentTypeTag:
1719 self.__initializeSimpleContent(args, dom_node)
1720
1721 - def __initializeSimpleContent (self, args, dom_node=None):
1722
1723
1724
1725
1726 value = self._TypeDefinition.Factory(_require_value=not self._isNil(), _dom_node=dom_node, _nil=self._isNil(), *args)
1727 if value._constructedWithValue():
1728 if self._isNil():
1729 raise pyxb.ContentInNilElementError(value)
1730 else:
1731 self.append(value)
1732
1733
1734 _ReservedSymbols = _TypeBinding_mixin._ReservedSymbols.union(set([ 'wildcardElements', 'wildcardAttributeMap',
1735 'xsdConstraintsOK', 'content', 'append', 'extend', 'value', 'reset' ]))
1736
1737
1738
1739 _ContentModel = None
1740
1741 @classmethod
1743 """Method used by generated code to associate the element binding with a use in this type.
1744
1745 This is necessary because all complex type classes appear in the
1746 module prior to any of the element instances (which reference type
1747 classes), so the association must be formed after the element
1748 instances are available."""
1749 return cls._UseForTag(element.name())._setElementBinding(element)
1750
1751 @classmethod
1753 """Return the ElementUse object corresponding to the element name.
1754
1755 @param tag: The L{ExpandedName} of an element in the class."""
1756 rv = cls._ElementMap.get(tag)
1757 if (rv is None) and raise_if_fail:
1758 raise pyxb.NotAnElementError(tag, cls)
1759 return rv
1760
1762 """Generate a list of children in the order in which they should be
1763 added to the parent when creating a DOM representation of this
1764 object.
1765
1766 @note: This is only used when L{pyxb.RequireValidWhenGenerating} has
1767 disabled validation. Consequently, it may not generate valid XML.
1768 """
1769 order = []
1770 for eu in self._ElementMap.values():
1771 value = eu.value(self)
1772 if value is None:
1773 continue
1774 if isinstance(value, list) and eu.isPlural():
1775 order.extend([ (eu, _v) for _v in value ])
1776 continue
1777 order.append( (eu, value) )
1778 return order
1779
1781 """Provide the child elements and non-element content in an order
1782 consistent with the content model.
1783
1784 Returns a sequence of tuples representing a valid path through the
1785 content model where each transition corresponds to one of the member
1786 element instances within this instance. The tuple is a pair
1787 comprising the L{content.ElementUse} instance and the value for the
1788 transition.
1789
1790 If the content of the instance does not validate against the content
1791 model, C{None} is returned.
1792
1793 The base class implementation uses the
1794 L{content.ParticleModel.validate} method. Subclasses may desire to
1795 override this in cases where the desired order is not maintained by
1796 model interpretation (for example, when an "all" model is used and the
1797 original element order is desired). See L{__childrenForDOM} as an
1798 example of an alternative approach.
1799
1800 @return: C{None} or a list as described above.
1801 """
1802 if self._ContentTypeTag in (self._CT_EMPTY, self._CT_SIMPLE):
1803 return []
1804
1805 if self._ContentModel is None:
1806 raise pyxb.NoContentModel(self)
1807 path = self._ContentModel.validate(self._symbolSet())
1808 if path is not None:
1809 ( symbols, sequence ) = path
1810 if 0 == len(symbols):
1811 return sequence
1812 raise pyxb.BindingValidationError('Ungenerated symbols: %s' % (symbols,) )
1813 return None
1814
1816 """Return a map from L{content.ElementUse} instances to a list of
1817 values associated with that use.
1818
1819 This is used as the set of symbols available for transitions when
1820 validating content against a model. Note that the order of values
1821 within a use is likely to be significant, although the model cannot
1822 detect this.
1823
1824 The value C{None} should be used to provide a list of wildcard
1825 members.
1826
1827 If an element use has no associated values, it must not appear in the
1828 returned map.
1829 """
1830 rv = { }
1831 for eu in self._ElementMap.values():
1832 value = eu.value(self)
1833 if value is None:
1834 continue
1835 converter = eu.elementBinding().compatibleValue
1836 if eu.isPlural():
1837 if 0 < len(value):
1838 rv[eu] = [ converter(_v) for _v in value ]
1839 else:
1840 rv[eu] = [ converter(value)]
1841 wce = self.wildcardElements()
1842 if (wce is not None) and (0 < len(wce)):
1843 rv[None] = wce[:]
1844 return rv
1845
1849
1870
1880
1882 """Validate the content against the simple type.
1883
1884 @return: C{True} if the content validates against its type.
1885 @raise pyxb.NotSimpleContentError: this type does not have simple content.
1886 @raise pyxb.MissingContentError: the content of this type has not been set
1887 """
1888
1889 if self._CT_SIMPLE != self._ContentTypeTag:
1890 raise pyxb.NotSimpleContentError(self)
1891 if self._isNil():
1892 return True
1893 if self.value() is None:
1894 raise pyxb.MissingContentError(self)
1895 return self.value().xsdConstraintsOK()
1896
1897 __content = None
1898 - def content (self):
1899 """Return the content of the element.
1900
1901 This must be a complex type with complex content. The return value is
1902 a list of the element and non-element content in the order in which it
1903 was added.
1904 @raise pyxb.NotComplexContentError: this is not a complex type with mixed or element-only content
1905 """
1906 if self._ContentTypeTag in (self._CT_EMPTY, self._CT_SIMPLE):
1907 raise pyxb.NotComplexContentError(str(self._ExpandedName))
1908 return self.__content
1909
1911 """Return the value of the element.
1912
1913 This must be a complex type with simple content. The returned value
1914 is expected to be an instance of some L{simpleTypeDefinition} class.
1915
1916 @raise pyxb.NotSimpleContentError: this is not a complex type with simple content
1917 """
1918 if self._CT_SIMPLE != self._ContentTypeTag:
1919 raise pyxb.NotSimpleContentError('%s (%s)' % (str(self._ExpandedName), type(self)))
1920 return self.__content
1921
1922 - def _resetContent (self):
1923 if self._ContentTypeTag in (self._CT_MIXED, self._CT_ELEMENT_ONLY):
1924 self.__setContent([])
1925 else:
1926 self.__setContent(None)
1927
1928 __modelState = None
1945
1946 @classmethod
1948 """Determine what the given name means as an element in this type.
1949
1950 Normally, C{element_name} identifies an element definition within this
1951 type. If so, the returned C{element_use} identifies that definition,
1952 and the C{element_binding} is extracted from that use.
1953
1954 It may also be that the C{element_name} does not appear as an element
1955 definition, but that it identifies a global element. In that case,
1956 the returned C{element_binding} identifies the global element. If,
1957 further, that element is a member of a substitution group which does
1958 have an element definition in this class, then the returned
1959 C{element_use} identifies that definition.
1960
1961 If a non-C{None} C{element_use} is returned, there will be an
1962 associated C{element_binding}. However, it is possible to return a
1963 non-C{None} C{element_binding}, but C{None} as the C{element_use}. In
1964 that case, the C{element_binding} can be used to create a binding
1965 instance, but the content model will have to treat it as a wildcard.
1966
1967 @param element_name: The name of the element in this type, either an
1968 expanded name or a local name if the element has an absent namespace.
1969
1970 @return: C{( element_binding, element_use )}
1971 """
1972 element_use = cls._ElementMap.get(element_name)
1973 element_binding = None
1974 if element_use is None:
1975 try:
1976 element_binding = element_name.elementBinding()
1977 except pyxb.NamespaceError:
1978 pass
1979 if element_binding is not None:
1980 element_use = element_binding.findSubstituendUse(cls)
1981 else:
1982 element_binding = element_use.elementBinding()
1983 return (element_binding, element_use)
1984
1985 - def append (self, value, element_use=None, maybe_element=True, _fallback_namespace=None, require_validation=True, _from_xml=False):
1986 """Add the value to the instance.
1987
1988 The value should be a DOM node or other value that is or can be
1989 converted to a binding instance. If the instance has a DFA state, the
1990 value must be permitted by the content model.
1991
1992 @raise pyxb.ExtraContentError: the value is not permitted at the
1993 current state of the content model.
1994 """
1995
1996
1997
1998 element_binding = None
1999 if element_use is not None:
2000 from pyxb.binding import content
2001 assert isinstance(element_use, content.ElementUse)
2002 element_binding = element_use.elementBinding()
2003 assert element_binding is not None
2004
2005 if isinstance(value, xml.dom.Node):
2006 _from_xml = True
2007 assert maybe_element
2008 assert element_binding is None
2009 node = value
2010 require_validation = pyxb._ParsingRequiresValid
2011 if xml.dom.Node.COMMENT_NODE == node.nodeType:
2012
2013
2014 return self
2015 if node.nodeType in (xml.dom.Node.TEXT_NODE, xml.dom.Node.CDATA_SECTION_NODE):
2016 value = node.data
2017 maybe_element = False
2018 else:
2019
2020 assert xml.dom.Node.ELEMENT_NODE == node.nodeType
2021 expanded_name = pyxb.namespace.ExpandedName(node, fallback_namespace=_fallback_namespace)
2022 (element_binding, element_use) = self._ElementBindingUseForName(expanded_name)
2023 if element_binding is not None:
2024 value = element_binding._createFromDOM(node, expanded_name, _fallback_namespace=_fallback_namespace)
2025 else:
2026
2027
2028 try:
2029 ns = expanded_name.namespace()
2030 if ns is not None:
2031 for mr in ns.moduleRecords():
2032 try:
2033 if (mr.module() is None) and (mr.modulePath() is not None):
2034 _log.info('Importing %s to get binding for wildcard %s', mr.modulePath(), expanded_name)
2035 mod = __import__(mr.modulePath())
2036 for c in mr.modulePath().split('.')[1:]:
2037 mod = getattr(mod, c)
2038 mr._setModule(mod)
2039
2040
2041
2042
2043
2044
2045
2046 if mr.module() is not None:
2047 value = mr.module().CreateFromDOM(node)
2048 elif mr.namespace() != pyxb.namespace.XMLSchema:
2049 _log.warning('No bindings available for %s', expanded_name)
2050 break
2051 except pyxb.UnrecognizedElementError, e:
2052 _log.info('Ignoring unrecognized element when creating binding for wildcard %s', expanded_name)
2053 except pyxb.PyXBException, e:
2054 _log.warning('Ignoring error when creating binding for wildcard %s', expanded_name, exc_info=e)
2055 except Exception:
2056 _log.exception('Unable to convert DOM node %s to Python instance', expanded_name)
2057 if (not maybe_element) and isinstance(value, basestring) and (self._ContentTypeTag in (self._CT_EMPTY, self._CT_ELEMENT_ONLY)):
2058 if (0 == len(value.strip())) and not self._isNil():
2059 return self
2060 if self._isNil() and not self._IsSimpleTypeContent():
2061 raise pyxb.ExtraContentError('%s: Content %s present in element with xsi:nil' % (type(self), value))
2062 if maybe_element and (self.__modelState is not None):
2063
2064 if not require_validation:
2065 if element_use is not None:
2066 element_use.setOrAppend(self, value)
2067 return self
2068 if self.wildcardElements() is not None:
2069 self._appendWildcardElement(value)
2070 return self
2071 raise pyxb.StructuralBadDocumentError('Validation is required when no element_use can be found')
2072 else:
2073 ( consumed, underflow_exc ) = self.__modelState.step(self, value, element_use)
2074 if consumed:
2075 return self
2076
2077
2078
2079 if (element_binding is not None) or isinstance(value, xml.dom.Node):
2080 raise pyxb.ExtraContentError('%s: Extra content %s starting with %s' % (self._ExpandedName, element_binding, value,))
2081
2082
2083
2084 if self._IsSimpleTypeContent():
2085 if self.__content is not None:
2086 raise pyxb.ExtraContentError('Extra content starting with %s (already have %s)' % (value, self.__content))
2087 if not self._isNil():
2088 if not isinstance(value, self._TypeDefinition):
2089 value = self._TypeDefinition.Factory(value, _from_xml=_from_xml)
2090 self.__setContent(value)
2091 if require_validation:
2092
2093
2094
2095 self.xsdConstraintsOK()
2096 return self
2097
2098
2099 if not self._IsMixed():
2100 raise pyxb.UnexpectedNonElementContentError(value)
2101 if isinstance(value, _TypeBinding_mixin):
2102 raise pyxb.ExtraContentError('Extra content starting with %s' % (value,))
2103
2104 self._addContent(value, element_binding)
2105 return self
2106
2112
2113 - def extend (self, value_list, _fallback_namespace=None, _from_xml=False):
2114 """Invoke L{append} for each value in the list, in turn."""
2115 [ self.append(_v, _fallback_namespace=_fallback_namespace, _from_xml=_from_xml) for _v in value_list ]
2116 return self
2117
2118 - def __setContent (self, value):
2120
2121 - def _addContent (self, child, element_binding):
2122
2123
2124
2125 assert not (self._ContentTypeTag in (self._CT_EMPTY, self._CT_SIMPLE))
2126 if isinstance(child, _TypeBinding_mixin) and (child._element() is None):
2127 child._setElement(element_binding)
2128 self.__content.append(child)
2129
2130 @classmethod
2133
2134 - def _postDOMValidate (self):
2135 if self._PerformValidation() and (not self._isNil()) and (self.__modelState is not None):
2136 self.__modelState.verifyComplete()
2137 self._validateAttributes()
2138 return self
2139
2140 - def _setContentFromDOM (self, node, _fallback_namespace):
2141 """Initialize the content of this element from the content of the DOM node."""
2142
2143 self.extend(node.childNodes[:], _fallback_namespace)
2144 return self._postDOMValidate()
2145
2153
2155 """Create a DOM element with the given tag holding the content of this instance."""
2156 element = parent
2157 self._setDOMFromAttributes(dom_support, element)
2158 if self._isNil():
2159 pass
2160 elif self._CT_EMPTY == self._ContentTypeTag:
2161 pass
2162 elif self._CT_SIMPLE == self._ContentTypeTag:
2163 assert self.value() is not None, '%s has no value' % (self,)
2164 element.appendChild(dom_support.document().createTextNode(self.value().xsdLiteral()))
2165 else:
2166 if pyxb._GenerationRequiresValid:
2167 order = self._validatedChildren()
2168 else:
2169 order = self.__childrenForDOM()
2170 if order is None:
2171 raise pyxb.DOMGenerationError('Binding value inconsistent with content model')
2172 for (eu, v) in order:
2173 assert v != self
2174 if eu is None:
2175 if isinstance(v, xml.dom.Node):
2176 dom_support.appendChild(v, element)
2177 else:
2178 v.toDOM(dom_support, parent)
2179 else:
2180 eu.toDOM(dom_support, parent, v)
2181 mixed_content = self.content()
2182 for mc in mixed_content:
2183 pass
2184 return getattr(super(complexTypeDefinition, self), '_toDOM_csc', lambda *_args,**_kw: dom_support)(dom_support, parent)
2185
2186 @classmethod
2188 """CTDs with simple content are simple; other CTDs are not."""
2189 return cls._CT_SIMPLE == cls._ContentTypeTag
2190
2191 @classmethod
2192 - def _description (cls, name_only=False, user_documentation=True):
2218
2219
2220
2221
2222