minicompat.py 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109
  1. """Python version compatibility support for minidom.
  2. This module contains internal implementation details and
  3. should not be imported; use xml.dom.minidom instead.
  4. """
  5. # This module should only be imported using "import *".
  6. #
  7. # The following names are defined:
  8. #
  9. # NodeList -- lightest possible NodeList implementation
  10. #
  11. # EmptyNodeList -- lightest possible NodeList that is guaranteed to
  12. # remain empty (immutable)
  13. #
  14. # StringTypes -- tuple of defined string types
  15. #
  16. # defproperty -- function used in conjunction with GetattrMagic;
  17. # using these together is needed to make them work
  18. # as efficiently as possible in both Python 2.2+
  19. # and older versions. For example:
  20. #
  21. # class MyClass(GetattrMagic):
  22. # def _get_myattr(self):
  23. # return something
  24. #
  25. # defproperty(MyClass, "myattr",
  26. # "return some value")
  27. #
  28. # For Python 2.2 and newer, this will construct a
  29. # property object on the class, which avoids
  30. # needing to override __getattr__(). It will only
  31. # work for read-only attributes.
  32. #
  33. # For older versions of Python, inheriting from
  34. # GetattrMagic will use the traditional
  35. # __getattr__() hackery to achieve the same effect,
  36. # but less efficiently.
  37. #
  38. # defproperty() should be used for each version of
  39. # the relevant _get_<property>() function.
  40. __all__ = ["NodeList", "EmptyNodeList", "StringTypes", "defproperty"]
  41. import xml.dom
  42. StringTypes = (str,)
  43. class NodeList(list):
  44. __slots__ = ()
  45. def item(self, index):
  46. if 0 <= index < len(self):
  47. return self[index]
  48. def _get_length(self):
  49. return len(self)
  50. def _set_length(self, value):
  51. raise xml.dom.NoModificationAllowedErr(
  52. "attempt to modify read-only attribute 'length'")
  53. length = property(_get_length, _set_length,
  54. doc="The number of nodes in the NodeList.")
  55. # For backward compatibility
  56. def __setstate__(self, state):
  57. if state is None:
  58. state = []
  59. self[:] = state
  60. class EmptyNodeList(tuple):
  61. __slots__ = ()
  62. def __add__(self, other):
  63. NL = NodeList()
  64. NL.extend(other)
  65. return NL
  66. def __radd__(self, other):
  67. NL = NodeList()
  68. NL.extend(other)
  69. return NL
  70. def item(self, index):
  71. return None
  72. def _get_length(self):
  73. return 0
  74. def _set_length(self, value):
  75. raise xml.dom.NoModificationAllowedErr(
  76. "attempt to modify read-only attribute 'length'")
  77. length = property(_get_length, _set_length,
  78. doc="The number of nodes in the NodeList.")
  79. def defproperty(klass, name, doc):
  80. get = getattr(klass, ("_get_" + name))
  81. def set(self, value, name=name):
  82. raise xml.dom.NoModificationAllowedErr(
  83. "attempt to modify read-only attribute " + repr(name))
  84. assert not hasattr(klass, "_set_" + name), \
  85. "expected not to find _set_" + name
  86. prop = property(get, set, doc=doc)
  87. setattr(klass, name, prop)