| Home | Trees | Indices | Help |
|
|---|
|
|
1 # -*- coding: utf-8 -*-
2
3 """
4 Tests specific to the extended etree API
5
6 Tests that apply to the general ElementTree API should go into
7 test_elementtree
8 """
9
10 import os.path
11 import unittest
12 import copy
13 import sys
14 import re
15 import gc
16 import operator
17 import tempfile
18 import gzip
19
20 this_dir = os.path.dirname(__file__)
21 if this_dir not in sys.path:
22 sys.path.insert(0, this_dir) # needed for Py3
23
24 from common_imports import etree, StringIO, BytesIO, HelperTestCase, fileInTestDir, read_file
25 from common_imports import SillyFileLike, LargeFileLikeUnicode, doctest, make_doctest
26 from common_imports import canonicalize, sorted, _str, _bytes
27
28 print("")
29 print("TESTED VERSION: %s" % etree.__version__)
30 print(" Python: " + repr(sys.version_info))
31 print(" lxml.etree: " + repr(etree.LXML_VERSION))
32 print(" libxml used: " + repr(etree.LIBXML_VERSION))
33 print(" libxml compiled: " + repr(etree.LIBXML_COMPILED_VERSION))
34 print(" libxslt used: " + repr(etree.LIBXSLT_VERSION))
35 print(" libxslt compiled: " + repr(etree.LIBXSLT_COMPILED_VERSION))
36 print("")
37
38 try:
39 _unicode = unicode
40 except NameError:
41 # Python 3
42 _unicode = str
43
45 """Tests only for etree, not ElementTree"""
46 etree = etree
47
49 self.assertTrue(isinstance(etree.__version__, _unicode))
50 self.assertTrue(isinstance(etree.LXML_VERSION, tuple))
51 self.assertEqual(len(etree.LXML_VERSION), 4)
52 self.assertTrue(isinstance(etree.LXML_VERSION[0], int))
53 self.assertTrue(isinstance(etree.LXML_VERSION[1], int))
54 self.assertTrue(isinstance(etree.LXML_VERSION[2], int))
55 self.assertTrue(isinstance(etree.LXML_VERSION[3], int))
56 self.assertTrue(etree.__version__.startswith(
57 str(etree.LXML_VERSION[0])))
58
60 if hasattr(self.etree, '__pyx_capi__'):
61 # newer Pyrex compatible C-API
62 self.assertTrue(isinstance(self.etree.__pyx_capi__, dict))
63 self.assertTrue(len(self.etree.__pyx_capi__) > 0)
64 else:
65 # older C-API mechanism
66 self.assertTrue(hasattr(self.etree, '_import_c_api'))
67
69 Element = self.etree.Element
70 el = Element('name')
71 self.assertEqual(el.tag, 'name')
72 el = Element('{}name')
73 self.assertEqual(el.tag, 'name')
74
76 Element = self.etree.Element
77 el = Element('name')
78 self.assertRaises(ValueError, Element, '{}')
79 self.assertRaises(ValueError, setattr, el, 'tag', '{}')
80
81 self.assertRaises(ValueError, Element, '{test}')
82 self.assertRaises(ValueError, setattr, el, 'tag', '{test}')
83
85 Element = self.etree.Element
86 self.assertRaises(ValueError, Element, 'p:name')
87 self.assertRaises(ValueError, Element, '{test}p:name')
88
89 el = Element('name')
90 self.assertRaises(ValueError, setattr, el, 'tag', 'p:name')
91
93 Element = self.etree.Element
94 self.assertRaises(ValueError, Element, "p'name")
95 self.assertRaises(ValueError, Element, 'p"name')
96
97 self.assertRaises(ValueError, Element, "{test}p'name")
98 self.assertRaises(ValueError, Element, '{test}p"name')
99
100 el = Element('name')
101 self.assertRaises(ValueError, setattr, el, 'tag', "p'name")
102 self.assertRaises(ValueError, setattr, el, 'tag', 'p"name')
103
105 Element = self.etree.Element
106 self.assertRaises(ValueError, Element, ' name ')
107 self.assertRaises(ValueError, Element, 'na me')
108 self.assertRaises(ValueError, Element, '{test} name')
109
110 el = Element('name')
111 self.assertRaises(ValueError, setattr, el, 'tag', ' name ')
112
114 Element = self.etree.Element
115 SubElement = self.etree.SubElement
116
117 el = Element('name')
118 self.assertRaises(ValueError, SubElement, el, '{}')
119 self.assertRaises(ValueError, SubElement, el, '{test}')
120
122 Element = self.etree.Element
123 SubElement = self.etree.SubElement
124
125 el = Element('name')
126 self.assertRaises(ValueError, SubElement, el, 'p:name')
127 self.assertRaises(ValueError, SubElement, el, '{test}p:name')
128
130 Element = self.etree.Element
131 SubElement = self.etree.SubElement
132
133 el = Element('name')
134 self.assertRaises(ValueError, SubElement, el, "p'name")
135 self.assertRaises(ValueError, SubElement, el, "{test}p'name")
136
137 self.assertRaises(ValueError, SubElement, el, 'p"name')
138 self.assertRaises(ValueError, SubElement, el, '{test}p"name')
139
141 Element = self.etree.Element
142 SubElement = self.etree.SubElement
143
144 el = Element('name')
145 self.assertRaises(ValueError, SubElement, el, ' name ')
146 self.assertRaises(ValueError, SubElement, el, 'na me')
147 self.assertRaises(ValueError, SubElement, el, '{test} name')
148
150 Element = self.etree.Element
151 SubElement = self.etree.SubElement
152
153 el = Element('name')
154 self.assertRaises(ValueError, SubElement, el, 'name', {'a b c' : 'abc'})
155 self.assertRaises(ValueError, SubElement, el, 'name', {'a' : 'a\0\n'})
156 self.assertEqual(0, len(el))
157
159 QName = self.etree.QName
160 self.assertRaises(ValueError, QName, '')
161 self.assertRaises(ValueError, QName, 'test', '')
162
164 QName = self.etree.QName
165 self.assertRaises(ValueError, QName, 'p:name')
166 self.assertRaises(ValueError, QName, 'test', 'p:name')
167
169 QName = self.etree.QName
170 self.assertRaises(ValueError, QName, ' name ')
171 self.assertRaises(ValueError, QName, 'na me')
172 self.assertRaises(ValueError, QName, 'test', ' name')
173
175 # ET doesn't have namespace/localname properties on QNames
176 QName = self.etree.QName
177 namespace, localname = 'http://myns', 'a'
178 qname = QName(namespace, localname)
179 self.assertEqual(namespace, qname.namespace)
180 self.assertEqual(localname, qname.localname)
181
183 # ET doesn't have namespace/localname properties on QNames
184 QName = self.etree.QName
185 qname1 = QName('http://myns', 'a')
186 a = self.etree.Element(qname1, nsmap={'p' : 'http://myns'})
187
188 qname2 = QName(a)
189 self.assertEqual(a.tag, qname1.text)
190 self.assertEqual(qname1.text, qname2.text)
191 self.assertEqual(qname1, qname2)
192
194 # ET doesn't resove QNames as text values
195 etree = self.etree
196 qname = etree.QName('http://myns', 'a')
197 a = etree.Element(qname, nsmap={'p' : 'http://myns'})
198 a.text = qname
199
200 self.assertEqual("p:a", a.text)
201
203 etree = self.etree
204 self.assertRaises(ValueError,
205 etree.Element, "root", nsmap={'"' : 'testns'})
206 self.assertRaises(ValueError,
207 etree.Element, "root", nsmap={'&' : 'testns'})
208 self.assertRaises(ValueError,
209 etree.Element, "root", nsmap={'a:b' : 'testns'})
210
212 # ET in Py 3.x has no "attrib.has_key()" method
213 XML = self.etree.XML
214
215 root = XML(_bytes('<foo bar="Bar" xmlns:ns="http://ns.codespeak.net/test" ns:baz="Baz" />'))
216 self.assertEqual(
217 True, root.attrib.has_key('bar'))
218 self.assertEqual(
219 False, root.attrib.has_key('baz'))
220 self.assertEqual(
221 False, root.attrib.has_key('hah'))
222 self.assertEqual(
223 True,
224 root.attrib.has_key('{http://ns.codespeak.net/test}baz'))
225
227 Element = self.etree.Element
228 root = Element("root")
229 root.set("attr", "TEST")
230 self.assertEqual("TEST", root.get("attr"))
231
233 # ElementTree accepts arbitrary attribute values
234 # lxml.etree allows only strings
235 Element = self.etree.Element
236 root = Element("root")
237 self.assertRaises(TypeError, root.set, "newattr", 5)
238 self.assertRaises(TypeError, root.set, "newattr", None)
239
241 XML = self.etree.XML
242 xml = _bytes('<test a="5" b="10" c="20"><x a="4" b="2"/></test>')
243
244 root = XML(xml)
245 self.etree.strip_attributes(root, 'a')
246 self.assertEqual(_bytes('<test b="10" c="20"><x b="2"></x></test>'),
247 self._writeElement(root))
248
249 root = XML(xml)
250 self.etree.strip_attributes(root, 'b', 'c')
251 self.assertEqual(_bytes('<test a="5"><x a="4"></x></test>'),
252 self._writeElement(root))
253
255 XML = self.etree.XML
256 xml = _bytes('<test xmlns:n="http://test/ns" a="6" b="10" c="20" n:a="5"><x a="4" n:b="2"/></test>')
257
258 root = XML(xml)
259 self.etree.strip_attributes(root, 'a')
260 self.assertEqual(
261 _bytes('<test xmlns:n="http://test/ns" b="10" c="20" n:a="5"><x n:b="2"></x></test>'),
262 self._writeElement(root))
263
264 root = XML(xml)
265 self.etree.strip_attributes(root, '{http://test/ns}a', 'c')
266 self.assertEqual(
267 _bytes('<test xmlns:n="http://test/ns" a="6" b="10"><x a="4" n:b="2"></x></test>'),
268 self._writeElement(root))
269
270 root = XML(xml)
271 self.etree.strip_attributes(root, '{http://test/ns}*')
272 self.assertEqual(
273 _bytes('<test xmlns:n="http://test/ns" a="6" b="10" c="20"><x a="4"></x></test>'),
274 self._writeElement(root))
275
277 XML = self.etree.XML
278 xml = _bytes('<test><a><b><c/></b></a><x><a><b/><c/></a></x></test>')
279
280 root = XML(xml)
281 self.etree.strip_elements(root, 'a')
282 self.assertEqual(_bytes('<test><x></x></test>'),
283 self._writeElement(root))
284
285 root = XML(xml)
286 self.etree.strip_elements(root, 'b', 'c', 'X', 'Y', 'Z')
287 self.assertEqual(_bytes('<test><a></a><x><a></a></x></test>'),
288 self._writeElement(root))
289
290 root = XML(xml)
291 self.etree.strip_elements(root, 'c')
292 self.assertEqual(_bytes('<test><a><b></b></a><x><a><b></b></a></x></test>'),
293 self._writeElement(root))
294
296 XML = self.etree.XML
297 xml = _bytes('<test>TEST<n:a xmlns:n="urn:a">A<b>B<c xmlns="urn:c"/>C</b>BT</n:a>AT<x>X<a>A<b xmlns="urn:a"/>BT<c xmlns="urn:x"/>CT</a>AT</x>XT</test>')
298
299 root = XML(xml)
300 self.etree.strip_elements(root, 'a')
301 self.assertEqual(_bytes('<test>TEST<n:a xmlns:n="urn:a">A<b>B<c xmlns="urn:c"></c>C</b>BT</n:a>AT<x>X</x>XT</test>'),
302 self._writeElement(root))
303
304 root = XML(xml)
305 self.etree.strip_elements(root, '{urn:a}b', 'c')
306 self.assertEqual(_bytes('<test>TEST<n:a xmlns:n="urn:a">A<b>B<c xmlns="urn:c"></c>C</b>BT</n:a>AT<x>X<a>A<c xmlns="urn:x"></c>CT</a>AT</x>XT</test>'),
307 self._writeElement(root))
308
309 root = XML(xml)
310 self.etree.strip_elements(root, '{urn:a}*', 'c')
311 self.assertEqual(_bytes('<test>TEST<x>X<a>A<c xmlns="urn:x"></c>CT</a>AT</x>XT</test>'),
312 self._writeElement(root))
313
314 root = XML(xml)
315 self.etree.strip_elements(root, '{urn:a}*', 'c', with_tail=False)
316 self.assertEqual(_bytes('<test>TESTAT<x>X<a>ABT<c xmlns="urn:x"></c>CT</a>AT</x>XT</test>'),
317 self._writeElement(root))
318
337
363
390
416
435
448
450 # lxml.etree separates target and text
451 Element = self.etree.Element
452 SubElement = self.etree.SubElement
453 ProcessingInstruction = self.etree.ProcessingInstruction
454
455 a = Element('a')
456 a.append(ProcessingInstruction('foo', 'some more text'))
457 self.assertEqual(a[0].target, 'foo')
458 self.assertEqual(a[0].text, 'some more text')
459
461 XML = self.etree.XML
462 root = XML(_bytes("<test><?mypi my test ?></test>"))
463 self.assertEqual(root[0].target, "mypi")
464 self.assertEqual(root[0].text, "my test ")
465
467 XML = self.etree.XML
468 root = XML(_bytes("<test><?mypi my='1' test=\" abc \" quotes=\"' '\" only names ?></test>"))
469 self.assertEqual(root[0].target, "mypi")
470 self.assertEqual(root[0].get('my'), "1")
471 self.assertEqual(root[0].get('test'), " abc ")
472 self.assertEqual(root[0].get('quotes'), "' '")
473 self.assertEqual(root[0].get('only'), None)
474 self.assertEqual(root[0].get('names'), None)
475 self.assertEqual(root[0].get('nope'), None)
476
478 XML = self.etree.XML
479 root = XML(_bytes("<test><?mypi my='1' test=\" abc \" quotes=\"' '\" only names ?></test>"))
480 self.assertEqual(root[0].target, "mypi")
481 self.assertEqual(root[0].attrib['my'], "1")
482 self.assertEqual(root[0].attrib['test'], " abc ")
483 self.assertEqual(root[0].attrib['quotes'], "' '")
484 self.assertRaises(KeyError, root[0].attrib.__getitem__, 'only')
485 self.assertRaises(KeyError, root[0].attrib.__getitem__, 'names')
486 self.assertRaises(KeyError, root[0].attrib.__getitem__, 'nope')
487
489 # previously caused a crash
490 ProcessingInstruction = self.etree.ProcessingInstruction
491
492 a = ProcessingInstruction("PI", "ONE")
493 b = copy.deepcopy(a)
494 b.text = "ANOTHER"
495
496 self.assertEqual('ONE', a.text)
497 self.assertEqual('ANOTHER', b.text)
498
500 XML = self.etree.XML
501 tostring = self.etree.tostring
502 root = XML(_bytes("<?mypi my test ?><test/><!--comment -->"))
503 tree1 = self.etree.ElementTree(root)
504 self.assertEqual(_bytes("<?mypi my test ?><test/><!--comment -->"),
505 tostring(tree1))
506
507 tree2 = copy.deepcopy(tree1)
508 self.assertEqual(_bytes("<?mypi my test ?><test/><!--comment -->"),
509 tostring(tree2))
510
511 root2 = copy.deepcopy(tree1.getroot())
512 self.assertEqual(_bytes("<test/>"),
513 tostring(root2))
514
516 XML = self.etree.XML
517 tostring = self.etree.tostring
518 xml = _bytes('<!DOCTYPE test [\n<!ENTITY entity "tasty">\n]>\n<test/>')
519 root = XML(xml)
520 tree1 = self.etree.ElementTree(root)
521 self.assertEqual(xml, tostring(tree1))
522
523 tree2 = copy.deepcopy(tree1)
524 self.assertEqual(xml, tostring(tree2))
525
526 root2 = copy.deepcopy(tree1.getroot())
527 self.assertEqual(_bytes("<test/>"),
528 tostring(root2))
529
531 # ElementTree accepts arbitrary attribute values
532 # lxml.etree allows only strings
533 Element = self.etree.Element
534
535 root = Element("root")
536 root.set("attr", "TEST")
537 self.assertEqual("TEST", root.get("attr"))
538 self.assertRaises(TypeError, root.set, "newattr", 5)
539
541 fromstring = self.etree.fromstring
542 tostring = self.etree.tostring
543 XMLParser = self.etree.XMLParser
544
545 xml = _bytes('<a><!--A--><b><!-- B --><c/></b><!--C--></a>')
546 parser = XMLParser(remove_comments=True)
547 root = fromstring(xml, parser)
548 self.assertEqual(
549 _bytes('<a><b><c/></b></a>'),
550 tostring(root))
551
553 parse = self.etree.parse
554 tostring = self.etree.tostring
555 XMLParser = self.etree.XMLParser
556
557 xml = _bytes('<?test?><a><?A?><b><?B?><c/></b><?C?></a><?tail?>')
558
559 f = BytesIO(xml)
560 tree = parse(f)
561 self.assertEqual(
562 xml,
563 tostring(tree))
564
565 parser = XMLParser(remove_pis=True)
566 tree = parse(f, parser)
567 self.assertEqual(
568 _bytes('<a><b><c/></b></a>'),
569 tostring(tree))
570
572 # ET raises IOError only
573 parse = self.etree.parse
574 self.assertRaises(TypeError, parse, 'notthere.xml', object())
575
577 # ET removes comments
578 iterparse = self.etree.iterparse
579 tostring = self.etree.tostring
580
581 f = BytesIO('<a><!--A--><b><!-- B --><c/></b><!--C--></a>')
582 events = list(iterparse(f))
583 root = events[-1][1]
584 self.assertEqual(3, len(events))
585 self.assertEqual(
586 _bytes('<a><!--A--><b><!-- B --><c/></b><!--C--></a>'),
587 tostring(root))
588
590 # ET removes comments
591 iterparse = self.etree.iterparse
592 tostring = self.etree.tostring
593
594 def name(event, el):
595 if event == 'comment':
596 return el.text
597 else:
598 return el.tag
599
600 f = BytesIO('<a><!--A--><b><!-- B --><c/></b><!--C--></a>')
601 events = list(iterparse(f, events=('end', 'comment')))
602 root = events[-1][1]
603 self.assertEqual(6, len(events))
604 self.assertEqual(['A', ' B ', 'c', 'b', 'C', 'a'],
605 [ name(*item) for item in events ])
606 self.assertEqual(
607 _bytes('<a><!--A--><b><!-- B --><c/></b><!--C--></a>'),
608 tostring(root))
609
611 # ET removes pis
612 iterparse = self.etree.iterparse
613 tostring = self.etree.tostring
614 ElementTree = self.etree.ElementTree
615
616 def name(event, el):
617 if event == 'pi':
618 return (el.target, el.text)
619 else:
620 return el.tag
621
622 f = BytesIO('<?pia a?><a><?pib b?><b><?pic c?><c/></b><?pid d?></a><?pie e?>')
623 events = list(iterparse(f, events=('end', 'pi')))
624 root = events[-2][1]
625 self.assertEqual(8, len(events))
626 self.assertEqual([('pia','a'), ('pib','b'), ('pic','c'), 'c', 'b',
627 ('pid','d'), 'a', ('pie','e')],
628 [ name(*item) for item in events ])
629 self.assertEqual(
630 _bytes('<?pia a?><a><?pib b?><b><?pic c?><c/></b><?pid d?></a><?pie e?>'),
631 tostring(ElementTree(root)))
632
634 iterparse = self.etree.iterparse
635 tostring = self.etree.tostring
636
637 f = BytesIO('<a><!--A--><b><!-- B --><c/></b><!--C--></a>')
638 events = list(iterparse(f, remove_comments=True,
639 events=('end', 'comment')))
640 root = events[-1][1]
641 self.assertEqual(3, len(events))
642 self.assertEqual(['c', 'b', 'a'],
643 [ el.tag for (event, el) in events ])
644 self.assertEqual(
645 _bytes('<a><b><c/></b></a>'),
646 tostring(root))
647
649 iterparse = self.etree.iterparse
650 f = BytesIO('<a><b><c/></a>')
651 # ET raises ExpatError, lxml raises XMLSyntaxError
652 self.assertRaises(self.etree.XMLSyntaxError, list, iterparse(f))
653
655 iterparse = self.etree.iterparse
656 f = BytesIO("""
657 <a> \n \n <b> b test </b> \n
658
659 \n\t <c> \n </c> </a> \n """)
660 iterator = iterparse(f, remove_blank_text=True)
661 text = [ (element.text, element.tail)
662 for event, element in iterator ]
663 self.assertEqual(
664 [(" b test ", None), (" \n ", None), (None, None)],
665 text)
666
668 iterparse = self.etree.iterparse
669 f = BytesIO('<a><b><d/></b><c/></a>')
670
671 iterator = iterparse(f, tag="b", events=('start', 'end'))
672 events = list(iterator)
673 root = iterator.root
674 self.assertEqual(
675 [('start', root[0]), ('end', root[0])],
676 events)
677
679 iterparse = self.etree.iterparse
680 f = BytesIO('<a><b><d/></b><c/></a>')
681
682 iterator = iterparse(f, tag="*", events=('start', 'end'))
683 events = list(iterator)
684 self.assertEqual(
685 8,
686 len(events))
687
689 iterparse = self.etree.iterparse
690 f = BytesIO('<a xmlns="urn:test:1"><b><d/></b><c/></a>')
691
692 iterator = iterparse(f, tag="{urn:test:1}b", events=('start', 'end'))
693 events = list(iterator)
694 root = iterator.root
695 self.assertEqual(
696 [('start', root[0]), ('end', root[0])],
697 events)
698
700 iterparse = self.etree.iterparse
701 f = BytesIO('<a><b><d/></b><c/></a>')
702 iterator = iterparse(f, tag="{}b", events=('start', 'end'))
703 events = list(iterator)
704 root = iterator.root
705 self.assertEqual(
706 [('start', root[0]), ('end', root[0])],
707 events)
708
709 f = BytesIO('<a xmlns="urn:test:1"><b><d/></b><c/></a>')
710 iterator = iterparse(f, tag="{}b", events=('start', 'end'))
711 events = list(iterator)
712 root = iterator.root
713 self.assertEqual([], events)
714
716 iterparse = self.etree.iterparse
717 f = BytesIO('<a xmlns="urn:test:1"><b><d/></b><c/></a>')
718 iterator = iterparse(f, tag="{urn:test:1}*", events=('start', 'end'))
719 events = list(iterator)
720 self.assertEqual(8, len(events))
721
723 iterparse = self.etree.iterparse
724 f = BytesIO('<a xmlns="urn:test:1"><b><d/></b><c/></a>')
725 iterator = iterparse(f, tag="{}*", events=('start', 'end'))
726 events = list(iterator)
727 self.assertEqual([], events)
728
729 f = BytesIO('<a><b><d/></b><c/></a>')
730 iterator = iterparse(f, tag="{}*", events=('start', 'end'))
731 events = list(iterator)
732 self.assertEqual(8, len(events))
733
735 text = _str('Søk på nettet')
736 wrong_declaration = "<?xml version='1.0' encoding='UTF-8'?>"
737 xml_latin1 = (_str('%s<a>%s</a>') % (wrong_declaration, text)
738 ).encode('iso-8859-1')
739
740 self.assertRaises(self.etree.ParseError,
741 list, self.etree.iterparse(BytesIO(xml_latin1)))
742
744 text = _str('Søk på nettet', encoding="UTF-8")
745 wrong_declaration = "<?xml version='1.0' encoding='UTF-8'?>"
746 xml_latin1 = (_str('%s<a>%s</a>') % (wrong_declaration, text)
747 ).encode('iso-8859-1')
748
749 iterator = self.etree.iterparse(BytesIO(xml_latin1),
750 encoding="iso-8859-1")
751 self.assertEqual(1, len(list(iterator)))
752
753 a = iterator.root
754 self.assertEqual(a.text, text)
755
757 tostring = self.etree.tostring
758 f = BytesIO('<root><![CDATA[test]]></root>')
759 context = self.etree.iterparse(f, strip_cdata=False)
760 content = [ el.text for event,el in context ]
761
762 self.assertEqual(['test'], content)
763 self.assertEqual(_bytes('<root><![CDATA[test]]></root>'),
764 tostring(context.root))
765
769
771 self.etree.XMLParser(encoding="ascii")
772 self.etree.XMLParser(encoding="utf-8")
773 self.etree.XMLParser(encoding="iso-8859-1")
774
776 parser = self.etree.XMLParser(recover=True)
777
778 parser.feed('<?xml version=')
779 parser.feed('"1.0"?><ro')
780 parser.feed('ot><')
781 parser.feed('a test="works"')
782 parser.feed('><othertag/></root') # <a> not closed!
783 parser.feed('>')
784
785 root = parser.close()
786
787 self.assertEqual(root.tag, "root")
788 self.assertEqual(len(root), 1)
789 self.assertEqual(root[0].tag, "a")
790 self.assertEqual(root[0].get("test"), "works")
791 self.assertEqual(len(root[0]), 1)
792 self.assertEqual(root[0][0].tag, "othertag")
793 # FIXME: would be nice to get some errors logged ...
794 #self.assertTrue(len(parser.error_log) > 0, "error log is empty")
795
797 assertEqual = self.assertEqual
798 assertFalse = self.assertFalse
799
800 events = []
801 class Target(object):
802 def start(self, tag, attrib):
803 events.append("start")
804 assertFalse(attrib)
805 assertEqual("TAG", tag)
806 def end(self, tag):
807 events.append("end")
808 assertEqual("TAG", tag)
809 def close(self):
810 return "DONE" # no Element!
811
812 parser = self.etree.XMLParser(target=Target())
813 tree = self.etree.ElementTree()
814
815 self.assertRaises(TypeError,
816 tree.parse, BytesIO("<TAG/>"), parser=parser)
817 self.assertEqual(["start", "end"], events)
818
820 # ET doesn't call .close() on errors
821 events = []
822 class Target(object):
823 def start(self, tag, attrib):
824 events.append("start-" + tag)
825 def end(self, tag):
826 events.append("end-" + tag)
827 if tag == 'a':
828 raise ValueError("dead and gone")
829 def data(self, data):
830 events.append("data-" + data)
831 def close(self):
832 events.append("close")
833 return "DONE"
834
835 parser = self.etree.XMLParser(target=Target())
836
837 try:
838 parser.feed(_bytes('<root>A<a>ca</a>B</root>'))
839 done = parser.close()
840 self.fail("error expected, but parsing succeeded")
841 except ValueError:
842 done = 'value error received as expected'
843
844 self.assertEqual(["start-root", "data-A", "start-a",
845 "data-ca", "end-a", "close"],
846 events)
847
849 # ET doesn't call .close() on errors
850 events = []
851 class Target(object):
852 def start(self, tag, attrib):
853 events.append("start-" + tag)
854 def end(self, tag):
855 events.append("end-" + tag)
856 if tag == 'a':
857 raise ValueError("dead and gone")
858 def data(self, data):
859 events.append("data-" + data)
860 def close(self):
861 events.append("close")
862 return "DONE"
863
864 parser = self.etree.XMLParser(target=Target())
865
866 try:
867 done = self.etree.fromstring(_bytes('<root>A<a>ca</a>B</root>'),
868 parser=parser)
869 self.fail("error expected, but parsing succeeded")
870 except ValueError:
871 done = 'value error received as expected'
872
873 self.assertEqual(["start-root", "data-A", "start-a",
874 "data-ca", "end-a", "close"],
875 events)
876
878 events = []
879 class Target(object):
880 def start(self, tag, attrib):
881 events.append("start-" + tag)
882 def end(self, tag):
883 events.append("end-" + tag)
884 def data(self, data):
885 events.append("data-" + data)
886 def comment(self, text):
887 events.append("comment-" + text)
888 def close(self):
889 return "DONE"
890
891 parser = self.etree.XMLParser(target=Target())
892
893 parser.feed(_bytes('<!--a--><root>A<!--b--><sub/><!--c-->B</root><!--d-->'))
894 done = parser.close()
895
896 self.assertEqual("DONE", done)
897 self.assertEqual(["comment-a", "start-root", "data-A", "comment-b",
898 "start-sub", "end-sub", "comment-c", "data-B",
899 "end-root", "comment-d"],
900 events)
901
903 events = []
904 class Target(object):
905 def start(self, tag, attrib):
906 events.append("start-" + tag)
907 def end(self, tag):
908 events.append("end-" + tag)
909 def data(self, data):
910 events.append("data-" + data)
911 def pi(self, target, data):
912 events.append("pi-" + target + "-" + data)
913 def close(self):
914 return "DONE"
915
916 parser = self.etree.XMLParser(target=Target())
917
918 parser.feed(_bytes('<?test a?><root>A<?test b?>B</root><?test c?>'))
919 done = parser.close()
920
921 self.assertEqual("DONE", done)
922 self.assertEqual(["pi-test-a", "start-root", "data-A", "pi-test-b",
923 "data-B", "end-root", "pi-test-c"],
924 events)
925
927 events = []
928 class Target(object):
929 def start(self, tag, attrib):
930 events.append("start-" + tag)
931 def end(self, tag):
932 events.append("end-" + tag)
933 def data(self, data):
934 events.append("data-" + data)
935 def close(self):
936 return "DONE"
937
938 parser = self.etree.XMLParser(target=Target(),
939 strip_cdata=False)
940
941 parser.feed(_bytes('<root>A<a><![CDATA[ca]]></a>B</root>'))
942 done = parser.close()
943
944 self.assertEqual("DONE", done)
945 self.assertEqual(["start-root", "data-A", "start-a",
946 "data-ca", "end-a", "data-B", "end-root"],
947 events)
948
950 events = []
951 class Target(object):
952 def start(self, tag, attrib):
953 events.append("start-" + tag)
954 def end(self, tag):
955 events.append("end-" + tag)
956 def data(self, data):
957 events.append("data-" + data)
958 def close(self):
959 events.append("close")
960 return "DONE"
961
962 parser = self.etree.XMLParser(target=Target(),
963 recover=True)
964
965 parser.feed(_bytes('<root>A<a>ca</a>B</not-root>'))
966 done = parser.close()
967
968 self.assertEqual("DONE", done)
969 self.assertEqual(["start-root", "data-A", "start-a",
970 "data-ca", "end-a", "data-B",
971 "end-root", "close"],
972 events)
973
975 iterwalk = self.etree.iterwalk
976 root = self.etree.XML(_bytes('<a><b><d/></b><c/></a>'))
977
978 iterator = iterwalk(root, tag="b", events=('start', 'end'))
979 events = list(iterator)
980 self.assertEqual(
981 [('start', root[0]), ('end', root[0])],
982 events)
983
985 iterwalk = self.etree.iterwalk
986 root = self.etree.XML(_bytes('<a><b><d/></b><c/></a>'))
987
988 iterator = iterwalk(root, tag="*", events=('start', 'end'))
989 events = list(iterator)
990 self.assertEqual(
991 8,
992 len(events))
993
995 iterwalk = self.etree.iterwalk
996 root = self.etree.XML(_bytes('<a><b></b><c/></a>'))
997
998 events = list(iterwalk(root))
999 self.assertEqual(
1000 [('end', root[0]), ('end', root[1]), ('end', root)],
1001 events)
1002
1004 iterwalk = self.etree.iterwalk
1005 root = self.etree.XML(_bytes('<a><b></b><c/></a>'))
1006
1007 iterator = iterwalk(root, events=('start',))
1008 events = list(iterator)
1009 self.assertEqual(
1010 [('start', root), ('start', root[0]), ('start', root[1])],
1011 events)
1012
1014 iterwalk = self.etree.iterwalk
1015 root = self.etree.XML(_bytes('<a><b></b><c/></a>'))
1016
1017 iterator = iterwalk(root, events=('start','end'))
1018 events = list(iterator)
1019 self.assertEqual(
1020 [('start', root), ('start', root[0]), ('end', root[0]),
1021 ('start', root[1]), ('end', root[1]), ('end', root)],
1022 events)
1023
1025 iterwalk = self.etree.iterwalk
1026 root = self.etree.XML(_bytes('<a><b></b><c/></a>'))
1027
1028 iterator = iterwalk(root)
1029 for event, elem in iterator:
1030 elem.clear()
1031
1032 self.assertEqual(0,
1033 len(root))
1034
1036 iterwalk = self.etree.iterwalk
1037 root = self.etree.XML(_bytes('<a xmlns="ns1"><b><c xmlns="ns2"/></b></a>'))
1038
1039 attr_name = '{testns}bla'
1040 events = []
1041 iterator = iterwalk(root, events=('start','end','start-ns','end-ns'))
1042 for event, elem in iterator:
1043 events.append(event)
1044 if event == 'start':
1045 if elem.tag != '{ns1}a':
1046 elem.set(attr_name, 'value')
1047
1048 self.assertEqual(
1049 ['start-ns', 'start', 'start', 'start-ns', 'start',
1050 'end', 'end-ns', 'end', 'end', 'end-ns'],
1051 events)
1052
1053 self.assertEqual(
1054 None,
1055 root.get(attr_name))
1056 self.assertEqual(
1057 'value',
1058 root[0].get(attr_name))
1059
1061 iterwalk = self.etree.iterwalk
1062 root = self.etree.XML(_bytes('<a><b><d/></b><c/></a>'))
1063
1064 counts = []
1065 for event, elem in iterwalk(root):
1066 counts.append(len(list(elem.getiterator())))
1067 self.assertEqual(
1068 [1,2,1,4],
1069 counts)
1070
1072 parse = self.etree.parse
1073 parser = self.etree.XMLParser(dtd_validation=True)
1074 assertEqual = self.assertEqual
1075 test_url = _str("__nosuch.dtd")
1076
1077 class MyResolver(self.etree.Resolver):
1078 def resolve(self, url, id, context):
1079 assertEqual(url, test_url)
1080 return self.resolve_string(
1081 _str('''<!ENTITY myentity "%s">
1082 <!ELEMENT doc ANY>''') % url, context)
1083
1084 parser.resolvers.add(MyResolver())
1085
1086 xml = _str('<!DOCTYPE doc SYSTEM "%s"><doc>&myentity;</doc>') % test_url
1087 tree = parse(StringIO(xml), parser)
1088 root = tree.getroot()
1089 self.assertEqual(root.text, test_url)
1090
1092 parse = self.etree.parse
1093 parser = self.etree.XMLParser(dtd_validation=True)
1094 assertEqual = self.assertEqual
1095 test_url = _str("__nosuch.dtd")
1096
1097 class MyResolver(self.etree.Resolver):
1098 def resolve(self, url, id, context):
1099 assertEqual(url, test_url)
1100 return self.resolve_string(
1101 (_str('''<!ENTITY myentity "%s">
1102 <!ELEMENT doc ANY>''') % url).encode('utf-8'),
1103 context)
1104
1105 parser.resolvers.add(MyResolver())
1106
1107 xml = _str('<!DOCTYPE doc SYSTEM "%s"><doc>&myentity;</doc>') % test_url
1108 tree = parse(StringIO(xml), parser)
1109 root = tree.getroot()
1110 self.assertEqual(root.text, test_url)
1111
1113 parse = self.etree.parse
1114 parser = self.etree.XMLParser(dtd_validation=True)
1115 assertEqual = self.assertEqual
1116 test_url = _str("__nosuch.dtd")
1117
1118 class MyResolver(self.etree.Resolver):
1119 def resolve(self, url, id, context):
1120 assertEqual(url, test_url)
1121 return self.resolve_file(
1122 SillyFileLike(
1123 _str('''<!ENTITY myentity "%s">
1124 <!ELEMENT doc ANY>''') % url), context)
1125
1126 parser.resolvers.add(MyResolver())
1127
1128 xml = _str('<!DOCTYPE doc SYSTEM "%s"><doc>&myentity;</doc>') % test_url
1129 tree = parse(StringIO(xml), parser)
1130 root = tree.getroot()
1131 self.assertEqual(root.text, test_url)
1132
1134 parse = self.etree.parse
1135 parser = self.etree.XMLParser(attribute_defaults=True)
1136 assertEqual = self.assertEqual
1137 test_url = _str("__nosuch.dtd")
1138
1139 class MyResolver(self.etree.Resolver):
1140 def resolve(self, url, id, context):
1141 assertEqual(url, test_url)
1142 return self.resolve_filename(
1143 fileInTestDir('test.dtd'), context)
1144
1145 parser.resolvers.add(MyResolver())
1146
1147 xml = _str('<!DOCTYPE a SYSTEM "%s"><a><b/></a>') % test_url
1148 tree = parse(StringIO(xml), parser)
1149 root = tree.getroot()
1150 self.assertEqual(
1151 root.attrib, {'default': 'valueA'})
1152 self.assertEqual(
1153 root[0].attrib, {'default': 'valueB'})
1154
1156 parse = self.etree.parse
1157 parser = self.etree.XMLParser(attribute_defaults=True)
1158 assertEqual = self.assertEqual
1159 test_url = _str("__nosuch.dtd")
1160
1161 class MyResolver(self.etree.Resolver):
1162 def resolve(self, url, id, context):
1163 assertEqual(url, fileInTestDir(test_url))
1164 return self.resolve_filename(
1165 fileInTestDir('test.dtd'), context)
1166
1167 parser.resolvers.add(MyResolver())
1168
1169 xml = _str('<!DOCTYPE a SYSTEM "%s"><a><b/></a>') % test_url
1170 tree = parse(StringIO(xml), parser,
1171 base_url=fileInTestDir('__test.xml'))
1172 root = tree.getroot()
1173 self.assertEqual(
1174 root.attrib, {'default': 'valueA'})
1175 self.assertEqual(
1176 root[0].attrib, {'default': 'valueB'})
1177
1179 parse = self.etree.parse
1180 parser = self.etree.XMLParser(attribute_defaults=True)
1181 assertEqual = self.assertEqual
1182 test_url = _str("__nosuch.dtd")
1183
1184 class MyResolver(self.etree.Resolver):
1185 def resolve(self, url, id, context):
1186 assertEqual(url, test_url)
1187 return self.resolve_file(
1188 open(fileInTestDir('test.dtd'), 'rb'), context)
1189
1190 parser.resolvers.add(MyResolver())
1191
1192 xml = _str('<!DOCTYPE a SYSTEM "%s"><a><b/></a>') % test_url
1193 tree = parse(StringIO(xml), parser)
1194 root = tree.getroot()
1195 self.assertEqual(
1196 root.attrib, {'default': 'valueA'})
1197 self.assertEqual(
1198 root[0].attrib, {'default': 'valueB'})
1199
1201 parse = self.etree.parse
1202 parser = self.etree.XMLParser(load_dtd=True)
1203 assertEqual = self.assertEqual
1204 test_url = _str("__nosuch.dtd")
1205
1206 class check(object):
1207 resolved = False
1208
1209 class MyResolver(self.etree.Resolver):
1210 def resolve(self, url, id, context):
1211 assertEqual(url, test_url)
1212 check.resolved = True
1213 return self.resolve_empty(context)
1214
1215 parser.resolvers.add(MyResolver())
1216
1217 xml = _str('<!DOCTYPE doc SYSTEM "%s"><doc>&myentity;</doc>') % test_url
1218 self.assertRaises(etree.XMLSyntaxError, parse, StringIO(xml), parser)
1219 self.assertTrue(check.resolved)
1220
1222 parse = self.etree.parse
1223 parser = self.etree.XMLParser(dtd_validation=True)
1224
1225 class _LocalException(Exception):
1226 pass
1227
1228 class MyResolver(self.etree.Resolver):
1229 def resolve(self, url, id, context):
1230 raise _LocalException
1231
1232 parser.resolvers.add(MyResolver())
1233
1234 xml = '<!DOCTYPE doc SYSTEM "test"><doc>&myentity;</doc>'
1235 self.assertRaises(_LocalException, parse, BytesIO(xml), parser)
1236
1237 if etree.LIBXML_VERSION > (2,6,20):
1239 parse = self.etree.parse
1240 tostring = self.etree.tostring
1241 parser = self.etree.XMLParser(resolve_entities=False)
1242 Entity = self.etree.Entity
1243
1244 xml = _bytes('<!DOCTYPE doc SYSTEM "test"><doc>&myentity;</doc>')
1245 tree = parse(BytesIO(xml), parser)
1246 root = tree.getroot()
1247 self.assertEqual(root[0].tag, Entity)
1248 self.assertEqual(root[0].text, "&myentity;")
1249 self.assertEqual(root[0].tail, None)
1250 self.assertEqual(root[0].name, "myentity")
1251
1252 self.assertEqual(_bytes('<doc>&myentity;</doc>'),
1253 tostring(root))
1254
1256 xml = _bytes('''<!DOCTYPE root [ <!ENTITY nbsp " "> ]>
1257 <root>
1258 <child1/>
1259 <child2/>
1260 <child3> </child3>
1261 </root>''')
1262
1263 parser = self.etree.XMLParser(resolve_entities=False)
1264 root = etree.fromstring(xml, parser)
1265 self.assertEqual([ el.tag for el in root ],
1266 ['child1', 'child2', 'child3'])
1267
1268 root[0] = root[-1]
1269 self.assertEqual([ el.tag for el in root ],
1270 ['child3', 'child2'])
1271 self.assertEqual(root[0][0].text, ' ')
1272 self.assertEqual(root[0][0].name, 'nbsp')
1273
1275 Entity = self.etree.Entity
1276 Element = self.etree.Element
1277 tostring = self.etree.tostring
1278
1279 root = Element("root")
1280 root.append( Entity("test") )
1281
1282 self.assertEqual(root[0].tag, Entity)
1283 self.assertEqual(root[0].text, "&test;")
1284 self.assertEqual(root[0].tail, None)
1285 self.assertEqual(root[0].name, "test")
1286
1287 self.assertEqual(_bytes('<root>&test;</root>'),
1288 tostring(root))
1289
1291 Entity = self.etree.Entity
1292 self.assertEqual(Entity("test").text, '&test;')
1293 self.assertEqual(Entity("#17683").text, '䔓')
1294 self.assertEqual(Entity("#x1768").text, 'ᝨ')
1295 self.assertEqual(Entity("#x98AF").text, '颯')
1296
1298 Entity = self.etree.Entity
1299 self.assertRaises(ValueError, Entity, 'a b c')
1300 self.assertRaises(ValueError, Entity, 'a,b')
1301 self.assertRaises(ValueError, Entity, 'a\0b')
1302 self.assertRaises(ValueError, Entity, '#abc')
1303 self.assertRaises(ValueError, Entity, '#xxyz')
1304
1306 CDATA = self.etree.CDATA
1307 Element = self.etree.Element
1308 tostring = self.etree.tostring
1309
1310 root = Element("root")
1311 root.text = CDATA('test')
1312
1313 self.assertEqual('test',
1314 root.text)
1315 self.assertEqual(_bytes('<root><![CDATA[test]]></root>'),
1316 tostring(root))
1317
1319 CDATA = self.etree.CDATA
1320 Element = self.etree.Element
1321 root = Element("root")
1322
1323 root.text = CDATA("test")
1324 self.assertEqual('test', root.text)
1325
1326 root.text = CDATA(_str("test"))
1327 self.assertEqual('test', root.text)
1328
1329 self.assertRaises(TypeError, CDATA, 1)
1330
1332 CDATA = self.etree.CDATA
1333 Element = self.etree.Element
1334
1335 root = Element("root")
1336 cdata = CDATA('test')
1337
1338 self.assertRaises(TypeError,
1339 setattr, root, 'tail', cdata)
1340 self.assertRaises(TypeError,
1341 root.set, 'attr', cdata)
1342 self.assertRaises(TypeError,
1343 operator.setitem, root.attrib, 'attr', cdata)
1344
1346 tostring = self.etree.tostring
1347 parser = self.etree.XMLParser(strip_cdata=False)
1348 root = self.etree.XML(_bytes('<root><![CDATA[test]]></root>'), parser)
1349
1350 self.assertEqual('test', root.text)
1351 self.assertEqual(_bytes('<root><![CDATA[test]]></root>'),
1352 tostring(root))
1353
1355 tostring = self.etree.tostring
1356 parser = self.etree.XMLParser(strip_cdata=False)
1357 root = self.etree.XML(_bytes('<root><![CDATA[test]]></root>'), parser)
1358 self.assertEqual(_bytes('<root><![CDATA[test]]></root>'),
1359 tostring(root))
1360
1361 self.assertEqual(['test'], root.xpath('//text()'))
1362
1363 # TypeError in etree, AssertionError in ElementTree;
1365 Element = self.etree.Element
1366 SubElement = self.etree.SubElement
1367
1368 a = Element('a')
1369 b = SubElement(a, 'b')
1370
1371 self.assertRaises(TypeError,
1372 a.__setitem__, 0, 'foo')
1373
1375 Element = self.etree.Element
1376 root = Element('root')
1377 # raises AssertionError in ElementTree
1378 self.assertRaises(TypeError, root.append, None)
1379 self.assertRaises(TypeError, root.extend, [None])
1380 self.assertRaises(TypeError, root.extend, [Element('one'), None])
1381 self.assertEqual('one', root[0].tag)
1382
1384 Element = self.etree.Element
1385 SubElement = self.etree.SubElement
1386 root = Element('root')
1387 SubElement(root, 'a')
1388 SubElement(root, 'b')
1389
1390 self.assertEqual(['a', 'b'],
1391 [c.tag for c in root])
1392 root[1].addnext(root[0])
1393 self.assertEqual(['b', 'a'],
1394 [c.tag for c in root])
1395
1397 Element = self.etree.Element
1398 SubElement = self.etree.SubElement
1399 root = Element('root')
1400 SubElement(root, 'a')
1401 SubElement(root, 'b')
1402
1403 self.assertEqual(['a', 'b'],
1404 [c.tag for c in root])
1405 root[0].addprevious(root[1])
1406 self.assertEqual(['b', 'a'],
1407 [c.tag for c in root])
1408
1410 Element = self.etree.Element
1411 a = Element('a')
1412 b = Element('b')
1413 self.assertRaises(TypeError, a.addnext, b)
1414
1416 Element = self.etree.Element
1417 a = Element('a')
1418 b = Element('b')
1419 self.assertRaises(TypeError, a.addnext, b)
1420
1422 Element = self.etree.Element
1423 SubElement = self.etree.SubElement
1424 PI = self.etree.PI
1425 root = Element('root')
1426 SubElement(root, 'a')
1427 pi = PI('TARGET', 'TEXT')
1428 pi.tail = "TAIL"
1429
1430 self.assertEqual(_bytes('<root><a></a></root>'),
1431 self._writeElement(root))
1432 root[0].addprevious(pi)
1433 self.assertEqual(_bytes('<root><?TARGET TEXT?>TAIL<a></a></root>'),
1434 self._writeElement(root))
1435
1437 Element = self.etree.Element
1438 PI = self.etree.PI
1439 root = Element('root')
1440 pi = PI('TARGET', 'TEXT')
1441 pi.tail = "TAIL"
1442
1443 self.assertEqual(_bytes('<root></root>'),
1444 self._writeElement(root))
1445 root.addprevious(pi)
1446 self.assertEqual(_bytes('<?TARGET TEXT?>\n<root></root>'),
1447 self._writeElement(root))
1448
1450 Element = self.etree.Element
1451 SubElement = self.etree.SubElement
1452 PI = self.etree.PI
1453 root = Element('root')
1454 SubElement(root, 'a')
1455 pi = PI('TARGET', 'TEXT')
1456 pi.tail = "TAIL"
1457
1458 self.assertEqual(_bytes('<root><a></a></root>'),
1459 self._writeElement(root))
1460 root[0].addnext(pi)
1461 self.assertEqual(_bytes('<root><a></a><?TARGET TEXT?>TAIL</root>'),
1462 self._writeElement(root))
1463
1465 Element = self.etree.Element
1466 PI = self.etree.PI
1467 root = Element('root')
1468 pi = PI('TARGET', 'TEXT')
1469 pi.tail = "TAIL"
1470
1471 self.assertEqual(_bytes('<root></root>'),
1472 self._writeElement(root))
1473 root.addnext(pi)
1474 self.assertEqual(_bytes('<root></root>\n<?TARGET TEXT?>'),
1475 self._writeElement(root))
1476
1478 Element = self.etree.Element
1479 SubElement = self.etree.SubElement
1480 Comment = self.etree.Comment
1481 root = Element('root')
1482 SubElement(root, 'a')
1483 comment = Comment('TEXT ')
1484 comment.tail = "TAIL"
1485
1486 self.assertEqual(_bytes('<root><a></a></root>'),
1487 self._writeElement(root))
1488 root[0].addnext(comment)
1489 self.assertEqual(_bytes('<root><a></a><!--TEXT -->TAIL</root>'),
1490 self._writeElement(root))
1491
1493 Element = self.etree.Element
1494 Comment = self.etree.Comment
1495 root = Element('root')
1496 comment = Comment('TEXT ')
1497 comment.tail = "TAIL"
1498
1499 self.assertEqual(_bytes('<root></root>'),
1500 self._writeElement(root))
1501 root.addnext(comment)
1502 self.assertEqual(_bytes('<root></root>\n<!--TEXT -->'),
1503 self._writeElement(root))
1504
1506 Element = self.etree.Element
1507 SubElement = self.etree.SubElement
1508 Comment = self.etree.Comment
1509 root = Element('root')
1510 SubElement(root, 'a')
1511 comment = Comment('TEXT ')
1512 comment.tail = "TAIL"
1513
1514 self.assertEqual(_bytes('<root><a></a></root>'),
1515 self._writeElement(root))
1516 root[0].addprevious(comment)
1517 self.assertEqual(_bytes('<root><!--TEXT -->TAIL<a></a></root>'),
1518 self._writeElement(root))
1519
1521 Element = self.etree.Element
1522 Comment = self.etree.Comment
1523 root = Element('root')
1524 comment = Comment('TEXT ')
1525 comment.tail = "TAIL"
1526
1527 self.assertEqual(_bytes('<root></root>'),
1528 self._writeElement(root))
1529 root.addprevious(comment)
1530 self.assertEqual(_bytes('<!--TEXT -->\n<root></root>'),
1531 self._writeElement(root))
1532
1533 # ET's Elements have items() and key(), but not values()
1535 XML = self.etree.XML
1536
1537 root = XML(_bytes('<doc alpha="Alpha" beta="Beta" gamma="Gamma"/>'))
1538 values = root.values()
1539 values.sort()
1540 self.assertEqual(['Alpha', 'Beta', 'Gamma'], values)
1541
1542 # gives error in ElementTree
1544 Element = self.etree.Element
1545 Comment = self.etree.Comment
1546
1547 a = Element('a')
1548 a.append(Comment())
1549 self.assertEqual(
1550 _bytes('<a><!----></a>'),
1551 self._writeElement(a))
1552
1553 # ElementTree ignores comments
1555 ElementTree = self.etree.ElementTree
1556 tostring = self.etree.tostring
1557
1558 xml = _bytes('<a><b/><!----><c/></a>')
1559 f = BytesIO(xml)
1560 doc = ElementTree(file=f)
1561 a = doc.getroot()
1562 self.assertEqual(
1563 '',
1564 a[1].text)
1565 self.assertEqual(
1566 xml,
1567 tostring(a))
1568
1569 # ElementTree ignores comments
1571 ElementTree = self.etree.ElementTree
1572
1573 f = BytesIO('<a><b></b><!-- hoi --><c></c></a>')
1574 doc = ElementTree(file=f)
1575 a = doc.getroot()
1576 self.assertEqual(
1577 ' hoi ',
1578 a[1].text)
1579
1580 # does not raise an exception in ElementTree
1582 Element = self.etree.Element
1583 Comment = self.etree.Comment
1584
1585 c = Comment()
1586 el = Element('myel')
1587
1588 self.assertRaises(TypeError, c.append, el)
1589 self.assertRaises(TypeError, c.insert, 0, el)
1590 self.assertRaises(TypeError, c.set, "myattr", "test")
1591
1592 # test passing 'None' to dump
1595
1597 ElementTree = self.etree.ElementTree
1598
1599 f = BytesIO('<a xmlns:foo="http://www.infrae.com/ns/1"><foo:b/></a>')
1600 doc = ElementTree(file=f)
1601 a = doc.getroot()
1602 self.assertEqual(
1603 None,
1604 a.prefix)
1605 self.assertEqual(
1606 'foo',
1607 a[0].prefix)
1608
1610 ElementTree = self.etree.ElementTree
1611
1612 f = BytesIO('<a xmlns="http://www.infrae.com/ns/1"><b/></a>')
1613 doc = ElementTree(file=f)
1614 a = doc.getroot()
1615 self.assertEqual(
1616 None,
1617 a.prefix)
1618 self.assertEqual(
1619 None,
1620 a[0].prefix)
1621
1623 Element = self.etree.Element
1624 SubElement = self.etree.SubElement
1625
1626 a = Element('a')
1627 b = SubElement(a, 'b')
1628 c = SubElement(a, 'c')
1629 d = SubElement(b, 'd')
1630 self.assertEqual(
1631 None,
1632 a.getparent())
1633 self.assertEqual(
1634 a,
1635 b.getparent())
1636 self.assertEqual(
1637 b.getparent(),
1638 c.getparent())
1639 self.assertEqual(
1640 b,
1641 d.getparent())
1642
1644 XML = self.etree.XML
1645
1646 root = XML(_bytes('<doc><one/><two>Two</two>Hm<three/></doc>'))
1647 result = []
1648 for el in root.iterchildren():
1649 result.append(el.tag)
1650 self.assertEqual(['one', 'two', 'three'], result)
1651
1653 XML = self.etree.XML
1654
1655 root = XML(_bytes('<doc><one/><two>Two</two>Hm<three/></doc>'))
1656 result = []
1657 for el in root.iterchildren(reversed=True):
1658 result.append(el.tag)
1659 self.assertEqual(['three', 'two', 'one'], result)
1660
1662 XML = self.etree.XML
1663
1664 root = XML(_bytes('<doc><one/><two>Two</two>Hm<two>Bla</two></doc>'))
1665 result = []
1666 for el in root.iterchildren(tag='two'):
1667 result.append(el.text)
1668 self.assertEqual(['Two', 'Bla'], result)
1669
1671 XML = self.etree.XML
1672
1673 root = XML(_bytes('<doc><one/><two>Two</two>Hm<two>Bla</two></doc>'))
1674 result = []
1675 for el in root.iterchildren(reversed=True, tag='two'):
1676 result.append(el.text)
1677 self.assertEqual(['Bla', 'Two'], result)
1678
1680 XML = self.etree.XML
1681
1682 root = XML(_bytes('<doc><one/><two>Two</two>Hm<two>Bla</two><three/></doc>'))
1683 result = []
1684 for el in root.iterchildren(tag=['two', 'three']):
1685 result.append(el.text)
1686 self.assertEqual(['Two', 'Bla', None], result)
1687
1689 XML = self.etree.XML
1690
1691 root = XML(_bytes('<doc><one/><two>Two</two>Hm<two>Bla</two><three/></doc>'))
1692 result = []
1693 for el in root.iterchildren(reversed=True, tag=['two', 'three']):
1694 result.append(el.text)
1695 self.assertEqual([None, 'Bla', 'Two'], result)
1696
1698 Element = self.etree.Element
1699 SubElement = self.etree.SubElement
1700
1701 a = Element('a')
1702 b = SubElement(a, 'b')
1703 c = SubElement(a, 'c')
1704 d = SubElement(b, 'd')
1705 self.assertEqual(
1706 [],
1707 list(a.iterancestors()))
1708 self.assertEqual(
1709 [a],
1710 list(b.iterancestors()))
1711 self.assertEqual(
1712 [a],
1713 list(c.iterancestors()))
1714 self.assertEqual(
1715 [b, a],
1716 list(d.iterancestors()))
1717
1719 Element = self.etree.Element
1720 SubElement = self.etree.SubElement
1721
1722 a = Element('a')
1723 b = SubElement(a, 'b')
1724 c = SubElement(a, 'c')
1725 d = SubElement(b, 'd')
1726 self.assertEqual(
1727 [a],
1728 list(d.iterancestors(tag='a')))
1729 self.assertEqual(
1730 [b, a],
1731 list(d.iterancestors(tag='*')))
1732
1734 Element = self.etree.Element
1735 SubElement = self.etree.SubElement
1736
1737 a = Element('a')
1738 b = SubElement(a, 'b')
1739 c = SubElement(a, 'c')
1740 d = SubElement(b, 'd')
1741 self.assertEqual(
1742 [b, a],
1743 list(d.iterancestors(tag=('a', 'b'))))
1744 self.assertEqual(
1745 [],
1746 list(d.iterancestors(tag=('w', 'x', 'y', 'z'))))
1747 self.assertEqual(
1748 [],
1749 list(d.iterancestors(tag=('d', 'x'))))
1750 self.assertEqual(
1751 [b, a],
1752 list(d.iterancestors(tag=('b', '*'))))
1753 self.assertEqual(
1754 [b],
1755 list(d.iterancestors(tag=('b', 'c'))))
1756
1758 Element = self.etree.Element
1759 SubElement = self.etree.SubElement
1760
1761 a = Element('a')
1762 b = SubElement(a, 'b')
1763 c = SubElement(a, 'c')
1764 d = SubElement(b, 'd')
1765 e = SubElement(c, 'e')
1766
1767 self.assertEqual(
1768 [b, d, c, e],
1769 list(a.iterdescendants()))
1770 self.assertEqual(
1771 [],
1772 list(d.iterdescendants()))
1773
1775 Element = self.etree.Element
1776 SubElement = self.etree.SubElement
1777
1778 a = Element('a')
1779 b = SubElement(a, 'b')
1780 c = SubElement(a, 'c')
1781 d = SubElement(b, 'd')
1782 e = SubElement(c, 'e')
1783
1784 self.assertEqual(
1785 [],
1786 list(a.iterdescendants('a')))
1787 a2 = SubElement(e, 'a')
1788 self.assertEqual(
1789 [a2],
1790 list(a.iterdescendants('a')))
1791 self.assertEqual(
1792 [a2],
1793 list(c.iterdescendants('a')))
1794
1796 Element = self.etree.Element
1797 SubElement = self.etree.SubElement
1798
1799 a = Element('a')
1800 b = SubElement(a, 'b')
1801 c = SubElement(a, 'c')
1802 d = SubElement(b, 'd')
1803 e = SubElement(c, 'e')
1804
1805 self.assertEqual(
1806 [b, e],
1807 list(a.iterdescendants(tag=('a', 'b', 'e'))))
1808 a2 = SubElement(e, 'a')
1809 self.assertEqual(
1810 [b, a2],
1811 list(a.iterdescendants(tag=('a', 'b'))))
1812 self.assertEqual(
1813 [],
1814 list(c.iterdescendants(tag=('x', 'y', 'z'))))
1815 self.assertEqual(
1816 [b, d, c, e, a2],
1817 list(a.iterdescendants(tag=('x', 'y', 'z', '*'))))
1818
1820 Element = self.etree.Element
1821 SubElement = self.etree.SubElement
1822
1823 a = Element('a')
1824 b = SubElement(a, 'b')
1825 c = SubElement(a, 'c')
1826 d = SubElement(b, 'd')
1827 self.assertEqual(
1828 a,
1829 a.getroottree().getroot())
1830 self.assertEqual(
1831 a,
1832 b.getroottree().getroot())
1833 self.assertEqual(
1834 a,
1835 d.getroottree().getroot())
1836
1838 Element = self.etree.Element
1839 SubElement = self.etree.SubElement
1840
1841 a = Element('a')
1842 b = SubElement(a, 'b')
1843 c = SubElement(a, 'c')
1844 self.assertEqual(
1845 None,
1846 a.getnext())
1847 self.assertEqual(
1848 c,
1849 b.getnext())
1850 self.assertEqual(
1851 None,
1852 c.getnext())
1853
1855 Element = self.etree.Element
1856 SubElement = self.etree.SubElement
1857
1858 a = Element('a')
1859 b = SubElement(a, 'b')
1860 c = SubElement(a, 'c')
1861 d = SubElement(b, 'd')
1862 self.assertEqual(
1863 None,
1864 a.getprevious())
1865 self.assertEqual(
1866 b,
1867 c.getprevious())
1868 self.assertEqual(
1869 None,
1870 b.getprevious())
1871
1873 Element = self.etree.Element
1874 SubElement = self.etree.SubElement
1875
1876 a = Element('a')
1877 b = SubElement(a, 'b')
1878 c = SubElement(a, 'c')
1879 d = SubElement(b, 'd')
1880 self.assertEqual(
1881 [],
1882 list(a.itersiblings()))
1883 self.assertEqual(
1884 [c],
1885 list(b.itersiblings()))
1886 self.assertEqual(
1887 [],
1888 list(c.itersiblings()))
1889 self.assertEqual(
1890 [b],
1891 list(c.itersiblings(preceding=True)))
1892 self.assertEqual(
1893 [],
1894 list(b.itersiblings(preceding=True)))
1895
1897 Element = self.etree.Element
1898 SubElement = self.etree.SubElement
1899
1900 a = Element('a')
1901 b = SubElement(a, 'b')
1902 c = SubElement(a, 'c')
1903 d = SubElement(b, 'd')
1904 self.assertEqual(
1905 [],
1906 list(a.itersiblings(tag='XXX')))
1907 self.assertEqual(
1908 [c],
1909 list(b.itersiblings(tag='c')))
1910 self.assertEqual(
1911 [c],
1912 list(b.itersiblings(tag='*')))
1913 self.assertEqual(
1914 [b],
1915 list(c.itersiblings(preceding=True, tag='b')))
1916 self.assertEqual(
1917 [],
1918 list(c.itersiblings(preceding=True, tag='c')))
1919
1921 Element = self.etree.Element
1922 SubElement = self.etree.SubElement
1923
1924 a = Element('a')
1925 b = SubElement(a, 'b')
1926 c = SubElement(a, 'c')
1927 d = SubElement(b, 'd')
1928 e = SubElement(a, 'e')
1929 self.assertEqual(
1930 [],
1931 list(a.itersiblings(tag=('XXX', 'YYY'))))
1932 self.assertEqual(
1933 [c, e],
1934 list(b.itersiblings(tag=('c', 'd', 'e'))))
1935 self.assertEqual(
1936 [b],
1937 list(c.itersiblings(preceding=True, tag=('b', 'b', 'c', 'd'))))
1938 self.assertEqual(
1939 [c, b],
1940 list(e.itersiblings(preceding=True, tag=('c', '*'))))
1941
1943 parseid = self.etree.parseid
1944 XML = self.etree.XML
1945 xml_text = _bytes('''
1946 <!DOCTYPE document [
1947 <!ELEMENT document (h1,p)*>
1948 <!ELEMENT h1 (#PCDATA)>
1949 <!ATTLIST h1 myid ID #REQUIRED>
1950 <!ELEMENT p (#PCDATA)>
1951 <!ATTLIST p someid ID #REQUIRED>
1952 ]>
1953 <document>
1954 <h1 myid="chapter1">...</h1>
1955 <p id="note1" class="note">...</p>
1956 <p>Regular paragraph.</p>
1957 <p xml:id="xmlid">XML:ID paragraph.</p>
1958 <p someid="warn1" class="warning">...</p>
1959 </document>
1960 ''')
1961
1962 tree, dic = parseid(BytesIO(xml_text))
1963 root = tree.getroot()
1964 root2 = XML(xml_text)
1965 self.assertEqual(self._writeElement(root),
1966 self._writeElement(root2))
1967 expected = {
1968 "chapter1" : root[0],
1969 "xmlid" : root[3],
1970 "warn1" : root[4]
1971 }
1972 self.assertTrue("chapter1" in dic)
1973 self.assertTrue("warn1" in dic)
1974 self.assertTrue("xmlid" in dic)
1975 self._checkIDDict(dic, expected)
1976
1978 XMLDTDID = self.etree.XMLDTDID
1979 XML = self.etree.XML
1980 xml_text = _bytes('''
1981 <!DOCTYPE document [
1982 <!ELEMENT document (h1,p)*>
1983 <!ELEMENT h1 (#PCDATA)>
1984 <!ATTLIST h1 myid ID #REQUIRED>
1985 <!ELEMENT p (#PCDATA)>
1986 <!ATTLIST p someid ID #REQUIRED>
1987 ]>
1988 <document>
1989 <h1 myid="chapter1">...</h1>
1990 <p id="note1" class="note">...</p>
1991 <p>Regular paragraph.</p>
1992 <p xml:id="xmlid">XML:ID paragraph.</p>
1993 <p someid="warn1" class="warning">...</p>
1994 </document>
1995 ''')
1996
1997 root, dic = XMLDTDID(xml_text)
1998 root2 = XML(xml_text)
1999 self.assertEqual(self._writeElement(root),
2000 self._writeElement(root2))
2001 expected = {
2002 "chapter1" : root[0],
2003 "xmlid" : root[3],
2004 "warn1" : root[4]
2005 }
2006 self.assertTrue("chapter1" in dic)
2007 self.assertTrue("warn1" in dic)
2008 self.assertTrue("xmlid" in dic)
2009 self._checkIDDict(dic, expected)
2010
2012 XMLDTDID = self.etree.XMLDTDID
2013 XML = self.etree.XML
2014 xml_text = _bytes('''
2015 <document>
2016 <h1 myid="chapter1">...</h1>
2017 <p id="note1" class="note">...</p>
2018 <p>Regular paragraph.</p>
2019 <p someid="warn1" class="warning">...</p>
2020 </document>
2021 ''')
2022
2023 root, dic = XMLDTDID(xml_text)
2024 root2 = XML(xml_text)
2025 self.assertEqual(self._writeElement(root),
2026 self._writeElement(root2))
2027 expected = {}
2028 self._checkIDDict(dic, expected)
2029
2031 self.assertEqual(len(dic),
2032 len(expected))
2033 self.assertEqual(sorted(dic.items()),
2034 sorted(expected.items()))
2035 if sys.version_info < (3,):
2036 self.assertEqual(sorted(dic.iteritems()),
2037 sorted(expected.iteritems()))
2038 self.assertEqual(sorted(dic.keys()),
2039 sorted(expected.keys()))
2040 if sys.version_info < (3,):
2041 self.assertEqual(sorted(dic.iterkeys()),
2042 sorted(expected.iterkeys()))
2043 if sys.version_info < (3,):
2044 self.assertEqual(sorted(dic.values()),
2045 sorted(expected.values()))
2046 self.assertEqual(sorted(dic.itervalues()),
2047 sorted(expected.itervalues()))
2048
2050 etree = self.etree
2051
2052 r = {'foo': 'http://ns.infrae.com/foo'}
2053 e = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=r)
2054 self.assertEqual(
2055 'foo',
2056 e.prefix)
2057 self.assertEqual(
2058 _bytes('<foo:bar xmlns:foo="http://ns.infrae.com/foo"></foo:bar>'),
2059 self._writeElement(e))
2060
2062 etree = self.etree
2063
2064 r = {None: 'http://ns.infrae.com/foo'}
2065 e = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=r)
2066 self.assertEqual(
2067 None,
2068 e.prefix)
2069 self.assertEqual(
2070 '{http://ns.infrae.com/foo}bar',
2071 e.tag)
2072 self.assertEqual(
2073 _bytes('<bar xmlns="http://ns.infrae.com/foo"></bar>'),
2074 self._writeElement(e))
2075
2077 etree = self.etree
2078
2079 r = {None: 'http://ns.infrae.com/foo',
2080 'hoi': 'http://ns.infrae.com/hoi'}
2081 e = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=r)
2082 e.set('{http://ns.infrae.com/hoi}test', 'value')
2083 self.assertEqual(
2084 _bytes('<bar xmlns="http://ns.infrae.com/foo" xmlns:hoi="http://ns.infrae.com/hoi" hoi:test="value"></bar>'),
2085 self._writeElement(e))
2086
2088 etree = self.etree
2089 r = {None: 'http://ns.infrae.com/foo',
2090 'hoi': 'http://ns.infrae.com/hoi'}
2091 e = etree.Element('{http://ns.infrae.com/foo}z', nsmap=r)
2092 tree = etree.ElementTree(element=e)
2093 etree.SubElement(e, '{http://ns.infrae.com/hoi}x')
2094 self.assertEqual(
2095 _bytes('<z xmlns="http://ns.infrae.com/foo" xmlns:hoi="http://ns.infrae.com/hoi"><hoi:x></hoi:x></z>'),
2096 self._writeElement(e))
2097
2099 etree = self.etree
2100
2101 r = {None: 'http://ns.infrae.com/foo'}
2102 e1 = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=r)
2103 e2 = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=r)
2104
2105 e1.append(e2)
2106
2107 self.assertEqual(
2108 None,
2109 e1.prefix)
2110 self.assertEqual(
2111 None,
2112 e1[0].prefix)
2113 self.assertEqual(
2114 '{http://ns.infrae.com/foo}bar',
2115 e1.tag)
2116 self.assertEqual(
2117 '{http://ns.infrae.com/foo}bar',
2118 e1[0].tag)
2119
2121 etree = self.etree
2122
2123 r = {None: 'http://ns.infrae.com/BAR'}
2124 e1 = etree.Element('{http://ns.infrae.com/BAR}bar', nsmap=r)
2125 e2 = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=r)
2126
2127 e1.append(e2)
2128
2129 self.assertEqual(
2130 None,
2131 e1.prefix)
2132 self.assertNotEqual(
2133 None,
2134 e2.prefix)
2135 self.assertEqual(
2136 '{http://ns.infrae.com/BAR}bar',
2137 e1.tag)
2138 self.assertEqual(
2139 '{http://ns.infrae.com/foo}bar',
2140 e2.tag)
2141
2143 ns_href = "http://a.b.c"
2144 one = self.etree.fromstring(
2145 _bytes('<foo><bar xmlns:ns="%s"><ns:baz/></bar></foo>' % ns_href))
2146 baz = one[0][0]
2147
2148 two = self.etree.fromstring(
2149 _bytes('<root xmlns:ns="%s"/>' % ns_href))
2150 two.append(baz)
2151 del one # make sure the source document is deallocated
2152
2153 self.assertEqual('{%s}baz' % ns_href, baz.tag)
2154 self.assertEqual(
2155 _bytes('<root xmlns:ns="%s"><ns:baz/></root>' % ns_href),
2156 self.etree.tostring(two))
2157
2159 xml = _bytes('<foo xmlns="F" xmlns:x="x"><bar xmlns:ns="NS" xmlns:b="b" xmlns="B"><ns:baz/></bar></foo>')
2160 root = self.etree.fromstring(xml)
2161 self.assertEqual(xml,
2162 self.etree.tostring(root))
2163 self.etree.cleanup_namespaces(root)
2164 self.assertEqual(
2165 _bytes('<foo xmlns="F"><bar xmlns:ns="NS" xmlns="B"><ns:baz/></bar></foo>'),
2166 self.etree.tostring(root))
2167
2169 etree = self.etree
2170
2171 r = {None: 'http://ns.infrae.com/foo',
2172 'hoi': 'http://ns.infrae.com/hoi'}
2173 e = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=r)
2174 self.assertEqual(
2175 r,
2176 e.nsmap)
2177
2179 etree = self.etree
2180
2181 re = {None: 'http://ns.infrae.com/foo',
2182 'hoi': 'http://ns.infrae.com/hoi'}
2183 e = etree.Element('{http://ns.infrae.com/foo}bar', nsmap=re)
2184
2185 rs = {None: 'http://ns.infrae.com/honk',
2186 'top': 'http://ns.infrae.com/top'}
2187 s = etree.SubElement(e, '{http://ns.infrae.com/honk}bar', nsmap=rs)
2188
2189 r = re.copy()
2190 r.update(rs)
2191 self.assertEqual(re, e.nsmap)
2192 self.assertEqual(r, s.nsmap)
2193
2195 etree = self.etree
2196 el = etree.HTML('<hha:page-description>aa</hha:page-description>').find('.//page-description')
2197 self.assertEqual({'hha': None}, el.nsmap)
2198
2200 Element = self.etree.Element
2201 SubElement = self.etree.SubElement
2202
2203 a = Element('a')
2204 b = SubElement(a, 'b')
2205 c = SubElement(a, 'c')
2206 d = SubElement(b, 'd')
2207 e = SubElement(c, 'e')
2208 f = SubElement(c, 'f')
2209
2210 self.assertEqual(
2211 [a, b],
2212 list(a.getiterator('a', 'b')))
2213 self.assertEqual(
2214 [],
2215 list(a.getiterator('x', 'y')))
2216 self.assertEqual(
2217 [a, f],
2218 list(a.getiterator('f', 'a')))
2219 self.assertEqual(
2220 [c, e, f],
2221 list(c.getiterator('c', '*', 'a')))
2222 self.assertEqual(
2223 [],
2224 list(a.getiterator( (), () )))
2225
2227 Element = self.etree.Element
2228 SubElement = self.etree.SubElement
2229
2230 a = Element('a')
2231 b = SubElement(a, 'b')
2232 c = SubElement(a, 'c')
2233 d = SubElement(b, 'd')
2234 e = SubElement(c, 'e')
2235 f = SubElement(c, 'f')
2236
2237 self.assertEqual(
2238 [a, b],
2239 list(a.getiterator( ('a', 'b') )))
2240 self.assertEqual(
2241 [],
2242 list(a.getiterator( ('x', 'y') )))
2243 self.assertEqual(
2244 [a, f],
2245 list(a.getiterator( ('f', 'a') )))
2246 self.assertEqual(
2247 [c, e, f],
2248 list(c.getiterator( ('c', '*', 'a') )))
2249 self.assertEqual(
2250 [],
2251 list(a.getiterator( () )))
2252
2254 Element = self.etree.Element
2255 SubElement = self.etree.SubElement
2256
2257 a = Element('{a}a')
2258 b = SubElement(a, '{a}b')
2259 c = SubElement(a, '{a}c')
2260 d = SubElement(b, '{b}d')
2261 e = SubElement(c, '{a}e')
2262 f = SubElement(c, '{b}f')
2263 g = SubElement(c, 'g')
2264
2265 self.assertEqual(
2266 [a],
2267 list(a.getiterator('{a}a')))
2268 self.assertEqual(
2269 [],
2270 list(a.getiterator('{b}a')))
2271 self.assertEqual(
2272 [],
2273 list(a.getiterator('a')))
2274 self.assertEqual(
2275 [a,b,d,c,e,f,g],
2276 list(a.getiterator('*')))
2277 self.assertEqual(
2278 [f],
2279 list(c.getiterator('{b}*')))
2280 self.assertEqual(
2281 [d, f],
2282 list(a.getiterator('{b}*')))
2283 self.assertEqual(
2284 [g],
2285 list(a.getiterator('g')))
2286 self.assertEqual(
2287 [g],
2288 list(a.getiterator('{}g')))
2289 self.assertEqual(
2290 [g],
2291 list(a.getiterator('{}*')))
2292
2294 Element = self.etree.Element
2295 SubElement = self.etree.SubElement
2296
2297 a = Element('{a}a')
2298 b = SubElement(a, '{nsA}b')
2299 c = SubElement(b, '{nsB}b')
2300 d = SubElement(a, 'b')
2301 e = SubElement(a, '{nsA}e')
2302 f = SubElement(e, '{nsB}e')
2303 g = SubElement(e, 'e')
2304
2305 self.assertEqual(
2306 [b, c, d],
2307 list(a.getiterator('{*}b')))
2308 self.assertEqual(
2309 [e, f, g],
2310 list(a.getiterator('{*}e')))
2311 self.assertEqual(
2312 [a, b, c, d, e, f, g],
2313 list(a.getiterator('{*}*')))
2314
2316 Element = self.etree.Element
2317 Entity = self.etree.Entity
2318 SubElement = self.etree.SubElement
2319
2320 a = Element('a')
2321 b = SubElement(a, 'b')
2322 entity_b = Entity("TEST-b")
2323 b.append(entity_b)
2324
2325 self.assertEqual(
2326 [entity_b],
2327 list(a.getiterator(Entity)))
2328
2329 entity_a = Entity("TEST-a")
2330 a.append(entity_a)
2331
2332 self.assertEqual(
2333 [entity_b, entity_a],
2334 list(a.getiterator(Entity)))
2335
2336 self.assertEqual(
2337 [entity_b],
2338 list(b.getiterator(Entity)))
2339
2341 Element = self.etree.Element
2342 Comment = self.etree.Comment
2343 PI = self.etree.PI
2344 SubElement = self.etree.SubElement
2345
2346 a = Element('a')
2347 b = SubElement(a, 'b')
2348 a.append(Comment("test"))
2349 a.append(PI("pi", "content"))
2350 c = SubElement(a, 'c')
2351
2352 self.assertEqual(
2353 [a, b, c],
2354 list(a.getiterator(Element)))
2355
2357 # ElementTree iterates over everything here
2358 Element = self.etree.Element
2359 Comment = self.etree.Comment
2360 PI = self.etree.PI
2361 SubElement = self.etree.SubElement
2362
2363 a = Element('a')
2364 b = SubElement(a, 'b')
2365 a.append(Comment("test"))
2366 a.append(PI("pi", "content"))
2367 c = SubElement(a, 'c')
2368
2369 self.assertEqual(
2370 [a, b, c],
2371 list(a.getiterator('*')))
2372
2374 XML = self.etree.XML
2375 ElementTree = self.etree.ElementTree
2376 QName = self.etree.QName
2377 tree = ElementTree(XML(_bytes('<a><b><c/></b><b/><c><b/></c></a>')))
2378 self.assertEqual(tree.find(QName("c")), tree.getroot()[2])
2379
2381 XML = self.etree.XML
2382 ElementTree = self.etree.ElementTree
2383 QName = self.etree.QName
2384 tree = ElementTree(XML(_bytes('<a><b><c/></b><b/><c><b/></c></a>')))
2385 self.assertEqual(len(list(tree.findall(QName("c")))), 1)
2386
2388 XML = self.etree.XML
2389 ElementTree = self.etree.ElementTree
2390 QName = self.etree.QName
2391 tree = ElementTree(XML(
2392 _bytes('<a xmlns:x="X" xmlns:y="Y"><x:b><c/></x:b><b/><c><x:b/><b/></c><b/></a>')))
2393 self.assertEqual(len(list(tree.findall(QName("b")))), 2)
2394 self.assertEqual(len(list(tree.findall(QName("X", "b")))), 1)
2395
2397 XML = self.etree.XML
2398 root = XML(_bytes('<a xmlns:x="X" xmlns:y="Y"><x:b><c/></x:b><b/><c><x:b/><b/></c><b/></a>'))
2399 self.assertEqual(len(root.findall(".//{X}b")), 2)
2400 self.assertEqual(len(root.findall(".//{X}*")), 2)
2401 self.assertEqual(len(root.findall(".//b")), 3)
2402
2404 XML = self.etree.XML
2405 root = XML(_bytes('<a xmlns:x="X" xmlns:y="Y"><x:b><c/></x:b><b/><c><x:b/><b/></c><y:b/></a>'))
2406 nsmap = {'xx': 'X'}
2407 self.assertEqual(len(root.findall(".//xx:b", namespaces=nsmap)), 2)
2408 self.assertEqual(len(root.findall(".//xx:*", namespaces=nsmap)), 2)
2409 self.assertEqual(len(root.findall(".//b", namespaces=nsmap)), 2)
2410 nsmap = {'xx': 'Y'}
2411 self.assertEqual(len(root.findall(".//xx:b", namespaces=nsmap)), 1)
2412 self.assertEqual(len(root.findall(".//xx:*", namespaces=nsmap)), 1)
2413 self.assertEqual(len(root.findall(".//b", namespaces=nsmap)), 2)
2414
2416 XML = self.etree.XML
2417 root = XML(_bytes('<a xmlns:x="X" xmlns:y="Y"><x:b><c/></x:b><b/><c><x:b/><b/></c><y:b/></a>'))
2418 nsmap = {'xx': 'X'}
2419 self.assertEqual(len(root.findall(".//xx:b", namespaces=nsmap)), 2)
2420 self.assertEqual(len(root.findall(".//xx:*", namespaces=nsmap)), 2)
2421 self.assertEqual(len(root.findall(".//b", namespaces=nsmap)), 2)
2422 nsmap = {'xx': 'Y'}
2423 self.assertEqual(len(root.findall(".//xx:b", namespaces=nsmap)), 1)
2424 self.assertEqual(len(root.findall(".//xx:*", namespaces=nsmap)), 1)
2425 self.assertEqual(len(root.findall(".//b", namespaces=nsmap)), 2)
2426
2428 XML = self.etree.XML
2429 root = XML(_bytes('<a><b><c/></b><b/><c><b/><b/></c><b/></a>'))
2430 self.assertRaises(SyntaxError, root.findall, '')
2431 self.assertRaises(SyntaxError, root.findall, '//') # absolute path on Element
2432 self.assertRaises(SyntaxError, root.findall, './//')
2433
2435 etree = self.etree
2436 e = etree.Element('foo')
2437 for i in range(10):
2438 etree.SubElement(e, 'a%s' % i)
2439 for i in range(10):
2440 self.assertEqual(
2441 i,
2442 e.index(e[i]))
2443 self.assertEqual(
2444 3, e.index(e[3], 3))
2445 self.assertRaises(
2446 ValueError, e.index, e[3], 4)
2447 self.assertRaises(
2448 ValueError, e.index, e[3], 0, 2)
2449 self.assertRaises(
2450 ValueError, e.index, e[8], 0, -3)
2451 self.assertRaises(
2452 ValueError, e.index, e[8], -5, -3)
2453 self.assertEqual(
2454 8, e.index(e[8], 0, -1))
2455 self.assertEqual(
2456 8, e.index(e[8], -12, -1))
2457 self.assertEqual(
2458 0, e.index(e[0], -12, -1))
2459
2461 etree = self.etree
2462 e = etree.Element('foo')
2463 for i in range(10):
2464 el = etree.SubElement(e, 'a%s' % i)
2465 el.text = "text%d" % i
2466 el.tail = "tail%d" % i
2467
2468 child0 = e[0]
2469 child1 = e[1]
2470 child2 = e[2]
2471
2472 e.replace(e[0], e[1])
2473 self.assertEqual(
2474 9, len(e))
2475 self.assertEqual(
2476 child1, e[0])
2477 self.assertEqual(
2478 child1.text, "text1")
2479 self.assertEqual(
2480 child1.tail, "tail1")
2481 self.assertEqual(
2482 child0.tail, "tail0")
2483 self.assertEqual(
2484 child2, e[1])
2485
2486 e.replace(e[-1], e[0])
2487 self.assertEqual(
2488 child1, e[-1])
2489 self.assertEqual(
2490 child1.text, "text1")
2491 self.assertEqual(
2492 child1.tail, "tail1")
2493 self.assertEqual(
2494 child2, e[0])
2495
2497 etree = self.etree
2498 e = etree.Element('foo')
2499 for i in range(10):
2500 etree.SubElement(e, 'a%s' % i)
2501
2502 new_element = etree.Element("test")
2503 new_element.text = "TESTTEXT"
2504 new_element.tail = "TESTTAIL"
2505 child1 = e[1]
2506 e.replace(e[0], new_element)
2507 self.assertEqual(
2508 new_element, e[0])
2509 self.assertEqual(
2510 "TESTTEXT",
2511 e[0].text)
2512 self.assertEqual(
2513 "TESTTAIL",
2514 e[0].tail)
2515 self.assertEqual(
2516 child1, e[1])
2517
2519 Element = self.etree.Element
2520 SubElement = self.etree.SubElement
2521
2522 a = Element('a')
2523
2524 e = Element('e')
2525 f = Element('f')
2526 g = Element('g')
2527
2528 s = [e, f, g]
2529 a[::-1] = s
2530 self.assertEqual(
2531 [g, f, e],
2532 list(a))
2533
2535 Element = self.etree.Element
2536 SubElement = self.etree.SubElement
2537
2538 a = Element('a')
2539 b = SubElement(a, 'b')
2540 c = SubElement(a, 'c')
2541 d = SubElement(a, 'd')
2542 e = SubElement(a, 'e')
2543
2544 x = Element('x')
2545 y = Element('y')
2546
2547 a[1::2] = [x, y]
2548 self.assertEqual(
2549 [b, x, d, y],
2550 list(a))
2551
2553 Element = self.etree.Element
2554 SubElement = self.etree.SubElement
2555
2556 a = Element('a')
2557 b = SubElement(a, 'b')
2558 c = SubElement(a, 'c')
2559 d = SubElement(a, 'd')
2560 e = SubElement(a, 'e')
2561
2562 x = Element('x')
2563 y = Element('y')
2564
2565 a[1::-1] = [x, y]
2566 self.assertEqual(
2567 [y, x, d, e],
2568 list(a))
2569
2571 Element = self.etree.Element
2572 SubElement = self.etree.SubElement
2573
2574 a = Element('a')
2575 b = SubElement(a, 'b')
2576 c = SubElement(a, 'c')
2577 d = SubElement(a, 'd')
2578 e = SubElement(a, 'e')
2579
2580 x = Element('x')
2581 y = Element('y')
2582
2583 a[::-2] = [x, y]
2584 self.assertEqual(
2585 [b, y, d, x],
2586 list(a))
2587
2589 Element = self.etree.Element
2590 SubElement = self.etree.SubElement
2591 try:
2592 slice
2593 except NameError:
2594 print("slice() not found")
2595 return
2596
2597 a = Element('a')
2598 b = SubElement(a, 'b')
2599 c = SubElement(a, 'c')
2600 d = SubElement(a, 'd')
2601 e = SubElement(a, 'e')
2602
2603 x = Element('x')
2604 y = Element('y')
2605 z = Element('z')
2606
2607 self.assertRaises(
2608 ValueError,
2609 operator.setitem, a, slice(1,None,2), [x, y, z])
2610
2611 self.assertEqual(
2612 [b, c, d, e],
2613 list(a))
2614
2616 XML = self.etree.XML
2617 root = XML(_bytes('''<?xml version="1.0"?>
2618 <root><test>
2619
2620 <bla/></test>
2621 </root>
2622 '''))
2623
2624 self.assertEqual(
2625 [2, 2, 4],
2626 [ el.sourceline for el in root.getiterator() ])
2627
2629 parse = self.etree.parse
2630 tree = parse(fileInTestDir('include/test_xinclude.xml'))
2631
2632 self.assertEqual(
2633 [1, 2, 3],
2634 [ el.sourceline for el in tree.getiterator() ])
2635
2637 iterparse = self.etree.iterparse
2638 lines = [ el.sourceline for (event, el) in
2639 iterparse(fileInTestDir('include/test_xinclude.xml')) ]
2640
2641 self.assertEqual(
2642 [2, 3, 1],
2643 lines)
2644
2646 iterparse = self.etree.iterparse
2647 lines = [ el.sourceline for (event, el) in
2648 iterparse(fileInTestDir('include/test_xinclude.xml'),
2649 events=("start",)) ]
2650
2651 self.assertEqual(
2652 [1, 2, 3],
2653 lines)
2654
2656 Element = self.etree.Element
2657 SubElement = self.etree.SubElement
2658 el = Element("test")
2659 self.assertEqual(None, el.sourceline)
2660
2661 child = SubElement(el, "test")
2662 self.assertEqual(None, el.sourceline)
2663 self.assertEqual(None, child.sourceline)
2664
2666 etree = self.etree
2667 root = etree.XML(_bytes("<root/>"), base_url="http://no/such/url")
2668 docinfo = root.getroottree().docinfo
2669 self.assertEqual(docinfo.URL, "http://no/such/url")
2670
2672 etree = self.etree
2673 root = etree.XML(_bytes("<root/>"), base_url="http://no/such/url")
2674 docinfo = root.getroottree().docinfo
2675 self.assertEqual(docinfo.URL, "http://no/such/url")
2676 docinfo.URL = "https://secret/url"
2677 self.assertEqual(docinfo.URL, "https://secret/url")
2678
2680 etree = self.etree
2681 tree = etree.parse(BytesIO("<root/>"), base_url="http://no/such/url")
2682 docinfo = tree.docinfo
2683 self.assertEqual(docinfo.URL, "http://no/such/url")
2684
2686 etree = self.etree
2687 tree = etree.parse(fileInTestDir('include/test_xinclude.xml'),
2688 base_url="http://no/such/url")
2689 docinfo = tree.docinfo
2690 self.assertEqual(docinfo.URL, "http://no/such/url")
2691
2693 etree = self.etree
2694 root = etree.HTML(_bytes("<html/>"), base_url="http://no/such/url")
2695 docinfo = root.getroottree().docinfo
2696 self.assertEqual(docinfo.URL, "http://no/such/url")
2697
2699 etree = self.etree
2700 xml_header = '<?xml version="1.0" encoding="ascii"?>'
2701 pub_id = "-//W3C//DTD XHTML 1.0 Transitional//EN"
2702 sys_id = "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"
2703 doctype_string = '<!DOCTYPE html PUBLIC "%s" "%s">' % (pub_id, sys_id)
2704
2705 xml = _bytes(xml_header + doctype_string + '<html><body></body></html>')
2706
2707 tree = etree.parse(BytesIO(xml))
2708 docinfo = tree.docinfo
2709 self.assertEqual(docinfo.encoding, "ascii")
2710 self.assertEqual(docinfo.xml_version, "1.0")
2711 self.assertEqual(docinfo.public_id, pub_id)
2712 self.assertEqual(docinfo.system_url, sys_id)
2713 self.assertEqual(docinfo.root_name, 'html')
2714 self.assertEqual(docinfo.doctype, doctype_string)
2715
2717 etree = self.etree
2718 xml_header = '<?xml version="1.0" encoding="UTF-8"?>'
2719 sys_id = "some.dtd"
2720 doctype_string = '<!DOCTYPE html SYSTEM "%s">' % sys_id
2721 xml = _bytes(xml_header + doctype_string + '<html><body></body></html>')
2722
2723 tree = etree.parse(BytesIO(xml))
2724 docinfo = tree.docinfo
2725 self.assertEqual(docinfo.encoding, "UTF-8")
2726 self.assertEqual(docinfo.xml_version, "1.0")
2727 self.assertEqual(docinfo.public_id, None)
2728 self.assertEqual(docinfo.system_url, sys_id)
2729 self.assertEqual(docinfo.root_name, 'html')
2730 self.assertEqual(docinfo.doctype, doctype_string)
2731
2733 etree = self.etree
2734 xml = _bytes('<html><body></body></html>')
2735 tree = etree.parse(BytesIO(xml))
2736 docinfo = tree.docinfo
2737 self.assertEqual(docinfo.encoding, "UTF-8")
2738 self.assertEqual(docinfo.xml_version, "1.0")
2739 self.assertEqual(docinfo.public_id, None)
2740 self.assertEqual(docinfo.system_url, None)
2741 self.assertEqual(docinfo.root_name, 'html')
2742 self.assertEqual(docinfo.doctype, '')
2743
2745 etree = self.etree
2746 xml = _bytes('<!DOCTYPE root><root></root>')
2747 tree = etree.parse(BytesIO(xml))
2748 docinfo = tree.docinfo
2749 self.assertEqual(docinfo.encoding, "UTF-8")
2750 self.assertEqual(docinfo.xml_version, "1.0")
2751 self.assertEqual(docinfo.public_id, None)
2752 self.assertEqual(docinfo.system_url, None)
2753 self.assertEqual(docinfo.root_name, 'root')
2754 self.assertEqual(docinfo.doctype, '<!DOCTYPE root>')
2755
2757 etree = self.etree
2758 xml = _bytes('<!DOCTYPE root>\n<root/>')
2759 tree = etree.parse(BytesIO(xml))
2760 self.assertEqual(xml, etree.tostring(tree))
2761
2763 etree = self.etree
2764 pub_id = "-//W3C//DTD XHTML 1.0 Transitional//EN"
2765 sys_id = "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"
2766 doctype_string = _bytes('<!DOCTYPE html PUBLIC "%s" "%s">' % (pub_id, sys_id))
2767
2768 xml = _bytes('<!DOCTYPE root>\n<root/>')
2769 tree = etree.parse(BytesIO(xml))
2770 self.assertEqual(xml.replace(_bytes('<!DOCTYPE root>'), doctype_string),
2771 etree.tostring(tree, doctype=doctype_string))
2772
2774 etree = self.etree
2775 root = etree.XML(_bytes("<root/>"), base_url="http://no/such/url")
2776 self.assertEqual(root.base, "http://no/such/url")
2777 self.assertEqual(
2778 root.get('{http://www.w3.org/XML/1998/namespace}base'), None)
2779 root.base = "https://secret/url"
2780 self.assertEqual(root.base, "https://secret/url")
2781 self.assertEqual(
2782 root.get('{http://www.w3.org/XML/1998/namespace}base'),
2783 "https://secret/url")
2784
2786 etree = self.etree
2787 root = etree.XML(_bytes("<root/>"), base_url="http://no/such/url")
2788 self.assertEqual(root.base, "http://no/such/url")
2789 self.assertEqual(
2790 root.get('{http://www.w3.org/XML/1998/namespace}base'), None)
2791 root.set('{http://www.w3.org/XML/1998/namespace}base',
2792 "https://secret/url")
2793 self.assertEqual(root.base, "https://secret/url")
2794 self.assertEqual(
2795 root.get('{http://www.w3.org/XML/1998/namespace}base'),
2796 "https://secret/url")
2797
2799 etree = self.etree
2800 root = etree.HTML(_bytes("<html><body></body></html>"),
2801 base_url="http://no/such/url")
2802 self.assertEqual(root.base, "http://no/such/url")
2803
2805 etree = self.etree
2806 root = etree.HTML(_bytes('<html><head><base href="http://no/such/url"></head></html>'))
2807 self.assertEqual(root.base, "http://no/such/url")
2808
2810 # parse from a file object that returns unicode strings
2811 f = LargeFileLikeUnicode()
2812 tree = self.etree.parse(f)
2813 root = tree.getroot()
2814 self.assertTrue(root.tag.endswith('root'))
2815
2817 # check that DTDs that go in also go back out
2818 xml = _bytes('''\
2819 <!DOCTYPE test SYSTEM "test.dtd" [
2820 <!ENTITY entity "tasty">
2821 <!ELEMENT test (a)>
2822 <!ELEMENT a (#PCDATA)>
2823 ]>
2824 <test><a>test-test</a></test>\
2825 ''')
2826 tree = self.etree.parse(BytesIO(xml))
2827 self.assertEqual(self.etree.tostring(tree).replace(_bytes(" "), _bytes("")),
2828 xml.replace(_bytes(" "), _bytes("")))
2829
2831 Element = self.etree.Element
2832
2833 a = Element('a')
2834 self.assertRaises(ValueError, setattr, a, "text", 'ha\0ho')
2835 self.assertRaises(ValueError, setattr, a, "tail", 'ha\0ho')
2836
2837 self.assertRaises(ValueError, Element, 'ha\0ho')
2838
2840 Element = self.etree.Element
2841
2842 a = Element('a')
2843 self.assertRaises(ValueError, setattr, a, "text",
2844 _str('ha\0ho'))
2845 self.assertRaises(ValueError, setattr, a, "tail",
2846 _str('ha\0ho'))
2847
2848 self.assertRaises(ValueError, Element,
2849 _str('ha\0ho'))
2850
2852 Element = self.etree.Element
2853
2854 a = Element('a')
2855 self.assertRaises(ValueError, setattr, a, "text", 'ha\x07ho')
2856 self.assertRaises(ValueError, setattr, a, "text", 'ha\x02ho')
2857
2858 self.assertRaises(ValueError, setattr, a, "tail", 'ha\x07ho')
2859 self.assertRaises(ValueError, setattr, a, "tail", 'ha\x02ho')
2860
2861 self.assertRaises(ValueError, Element, 'ha\x07ho')
2862 self.assertRaises(ValueError, Element, 'ha\x02ho')
2863
2865 Element = self.etree.Element
2866
2867 a = Element('a')
2868 self.assertRaises(ValueError, setattr, a, "text",
2869 _str('ha\x07ho'))
2870 self.assertRaises(ValueError, setattr, a, "text",
2871 _str('ha\x02ho'))
2872
2873 self.assertRaises(ValueError, setattr, a, "tail",
2874 _str('ha\x07ho'))
2875 self.assertRaises(ValueError, setattr, a, "tail",
2876 _str('ha\x02ho'))
2877
2878 self.assertRaises(ValueError, Element,
2879 _str('ha\x07ho'))
2880 self.assertRaises(ValueError, Element,
2881 _str('ha\x02ho'))
2882
2884 Element = self.etree.Element
2885
2886 a = Element('a')
2887 self.assertRaises(ValueError, setattr, a, "text",
2888 _str('ha\u1234\x07ho'))
2889 self.assertRaises(ValueError, setattr, a, "text",
2890 _str('ha\u1234\x02ho'))
2891
2892 self.assertRaises(ValueError, setattr, a, "tail",
2893 _str('ha\u1234\x07ho'))
2894 self.assertRaises(ValueError, setattr, a, "tail",
2895 _str('ha\u1234\x02ho'))
2896
2897 self.assertRaises(ValueError, Element,
2898 _str('ha\u1234\x07ho'))
2899 self.assertRaises(ValueError, Element,
2900 _str('ha\u1234\x02ho'))
2901
2903 # ElementTree fails to serialize this
2904 tostring = self.etree.tostring
2905 Element = self.etree.Element
2906 SubElement = self.etree.SubElement
2907
2908 a = Element('a')
2909 b = SubElement(a, 'b')
2910 c = SubElement(a, 'c')
2911
2912 result = tostring(a, encoding='UTF-16')
2913 self.assertEqual(_bytes('<a><b></b><c></c></a>'),
2914 canonicalize(result))
2915
2917 # ElementTree raises an AssertionError here
2918 tostring = self.etree.tostring
2919 self.assertRaises(TypeError, self.etree.tostring, None)
2920
2922 tostring = self.etree.tostring
2923 Element = self.etree.Element
2924 SubElement = self.etree.SubElement
2925
2926 a = Element('a')
2927 b = SubElement(a, 'b')
2928 c = SubElement(a, 'c')
2929
2930 result = tostring(a)
2931 self.assertEqual(result, _bytes("<a><b/><c/></a>"))
2932
2933 result = tostring(a, pretty_print=False)
2934 self.assertEqual(result, _bytes("<a><b/><c/></a>"))
2935
2936 result = tostring(a, pretty_print=True)
2937 self.assertEqual(result, _bytes("<a>\n <b/>\n <c/>\n</a>\n"))
2938
2940 tostring = self.etree.tostring
2941 Element = self.etree.Element
2942 SubElement = self.etree.SubElement
2943
2944 a = Element('a')
2945 a.tail = "aTAIL"
2946 b = SubElement(a, 'b')
2947 b.tail = "bTAIL"
2948 c = SubElement(a, 'c')
2949
2950 result = tostring(a)
2951 self.assertEqual(result, _bytes("<a><b/>bTAIL<c/></a>aTAIL"))
2952
2953 result = tostring(a, with_tail=False)
2954 self.assertEqual(result, _bytes("<a><b/>bTAIL<c/></a>"))
2955
2956 result = tostring(a, with_tail=True)
2957 self.assertEqual(result, _bytes("<a><b/>bTAIL<c/></a>aTAIL"))
2958
2960 tostring = self.etree.tostring
2961 XML = self.etree.XML
2962 ElementTree = self.etree.ElementTree
2963 Element = self.etree.Element
2964
2965 tree = Element("root").getroottree()
2966 self.assertEqual(None, tree.docinfo.standalone)
2967
2968 tree = XML(_bytes("<root/>")).getroottree()
2969 self.assertEqual(None, tree.docinfo.standalone)
2970
2971 tree = XML(_bytes(
2972 "<?xml version='1.0' encoding='ASCII' standalone='yes'?>\n<root/>"
2973 )).getroottree()
2974 self.assertEqual(True, tree.docinfo.standalone)
2975
2976 tree = XML(_bytes(
2977 "<?xml version='1.0' encoding='ASCII' standalone='no'?>\n<root/>"
2978 )).getroottree()
2979 self.assertEqual(False, tree.docinfo.standalone)
2980
2982 tostring = self.etree.tostring
2983 XML = self.etree.XML
2984 ElementTree = self.etree.ElementTree
2985
2986 root = XML(_bytes("<root/>"))
2987
2988 tree = ElementTree(root)
2989 self.assertEqual(None, tree.docinfo.standalone)
2990
2991 result = tostring(root, xml_declaration=True, encoding="ASCII")
2992 self.assertEqual(result, _bytes(
2993 "<?xml version='1.0' encoding='ASCII'?>\n<root/>"))
2994
2995 result = tostring(root, xml_declaration=True, encoding="ASCII",
2996 standalone=True)
2997 self.assertEqual(result, _bytes(
2998 "<?xml version='1.0' encoding='ASCII' standalone='yes'?>\n<root/>"))
2999
3000 tree = ElementTree(XML(result))
3001 self.assertEqual(True, tree.docinfo.standalone)
3002
3003 result = tostring(root, xml_declaration=True, encoding="ASCII",
3004 standalone=False)
3005 self.assertEqual(result, _bytes(
3006 "<?xml version='1.0' encoding='ASCII' standalone='no'?>\n<root/>"))
3007
3008 tree = ElementTree(XML(result))
3009 self.assertEqual(False, tree.docinfo.standalone)
3010
3012 tostring = self.etree.tostring
3013 XML = self.etree.XML
3014 ElementTree = self.etree.ElementTree
3015
3016 root = XML(_bytes(
3017 "<?xml version='1.0' encoding='UTF-8' standalone='yes'?>\n<root/>"))
3018
3019 tree = ElementTree(root)
3020 self.assertEqual(True, tree.docinfo.standalone)
3021
3022 result = tostring(root, xml_declaration=True, encoding="ASCII")
3023 self.assertEqual(result, _bytes(
3024 "<?xml version='1.0' encoding='ASCII'?>\n<root/>"))
3025
3026 result = tostring(root, xml_declaration=True, encoding="ASCII",
3027 standalone=True)
3028 self.assertEqual(result, _bytes(
3029 "<?xml version='1.0' encoding='ASCII' standalone='yes'?>\n<root/>"))
3030
3032 tostring = self.etree.tostring
3033 Element = self.etree.Element
3034 SubElement = self.etree.SubElement
3035
3036 a = Element('a')
3037 a.text = "A"
3038 a.tail = "tail"
3039 b = SubElement(a, 'b')
3040 b.text = "B"
3041 b.tail = _str("Søk på nettet")
3042 c = SubElement(a, 'c')
3043 c.text = "C"
3044
3045 result = tostring(a, method="text", encoding="UTF-16")
3046
3047 self.assertEqual(_str('ABSøk på nettetCtail').encode("UTF-16"),
3048 result)
3049
3051 tostring = self.etree.tostring
3052 Element = self.etree.Element
3053 SubElement = self.etree.SubElement
3054
3055 a = Element('a')
3056 a.text = _str('Søk på nettetA')
3057 a.tail = "tail"
3058 b = SubElement(a, 'b')
3059 b.text = "B"
3060 b.tail = _str('Søk på nettetB')
3061 c = SubElement(a, 'c')
3062 c.text = "C"
3063
3064 self.assertRaises(UnicodeEncodeError,
3065 tostring, a, method="text")
3066
3067 self.assertEqual(
3068 _str('Søk på nettetABSøk på nettetBCtail').encode('utf-8'),
3069 tostring(a, encoding="UTF-8", method="text"))
3070
3072 tounicode = self.etree.tounicode
3073 Element = self.etree.Element
3074 SubElement = self.etree.SubElement
3075
3076 a = Element('a')
3077 b = SubElement(a, 'b')
3078 c = SubElement(a, 'c')
3079
3080 self.assertTrue(isinstance(tounicode(a), _unicode))
3081 self.assertEqual(_bytes('<a><b></b><c></c></a>'),
3082 canonicalize(tounicode(a)))
3083
3085 tounicode = self.etree.tounicode
3086 Element = self.etree.Element
3087 SubElement = self.etree.SubElement
3088
3089 a = Element('a')
3090 b = SubElement(a, 'b')
3091 c = SubElement(a, 'c')
3092 d = SubElement(c, 'd')
3093 self.assertTrue(isinstance(tounicode(b), _unicode))
3094 self.assertTrue(isinstance(tounicode(c), _unicode))
3095 self.assertEqual(_bytes('<b></b>'),
3096 canonicalize(tounicode(b)))
3097 self.assertEqual(_bytes('<c><d></d></c>'),
3098 canonicalize(tounicode(c)))
3099
3103
3105 tounicode = self.etree.tounicode
3106 Element = self.etree.Element
3107 SubElement = self.etree.SubElement
3108
3109 a = Element('a')
3110 b = SubElement(a, 'b')
3111 c = SubElement(a, 'c')
3112 d = SubElement(c, 'd')
3113 b.tail = 'Foo'
3114
3115 self.assertTrue(isinstance(tounicode(b), _unicode))
3116 self.assertTrue(tounicode(b) == '<b/>Foo' or
3117 tounicode(b) == '<b />Foo')
3118
3120 tounicode = self.etree.tounicode
3121 Element = self.etree.Element
3122 SubElement = self.etree.SubElement
3123
3124 a = Element('a')
3125 b = SubElement(a, 'b')
3126 c = SubElement(a, 'c')
3127
3128 result = tounicode(a)
3129 self.assertEqual(result, "<a><b/><c/></a>")
3130
3131 result = tounicode(a, pretty_print=False)
3132 self.assertEqual(result, "<a><b/><c/></a>")
3133
3134 result = tounicode(a, pretty_print=True)
3135 self.assertEqual(result, "<a>\n <b/>\n <c/>\n</a>\n")
3136
3138 tostring = self.etree.tostring
3139 Element = self.etree.Element
3140 SubElement = self.etree.SubElement
3141
3142 a = Element('a')
3143 b = SubElement(a, 'b')
3144 c = SubElement(a, 'c')
3145
3146 self.assertTrue(isinstance(tostring(a, encoding=_unicode), _unicode))
3147 self.assertEqual(_bytes('<a><b></b><c></c></a>'),
3148 canonicalize(tostring(a, encoding=_unicode)))
3149
3151 tostring = self.etree.tostring
3152 Element = self.etree.Element
3153 SubElement = self.etree.SubElement
3154
3155 a = Element('a')
3156 b = SubElement(a, 'b')
3157 c = SubElement(a, 'c')
3158 d = SubElement(c, 'd')
3159 self.assertTrue(isinstance(tostring(b, encoding=_unicode), _unicode))
3160 self.assertTrue(isinstance(tostring(c, encoding=_unicode), _unicode))
3161 self.assertEqual(_bytes('<b></b>'),
3162 canonicalize(tostring(b, encoding=_unicode)))
3163 self.assertEqual(_bytes('<c><d></d></c>'),
3164 canonicalize(tostring(c, encoding=_unicode)))
3165
3167 tostring = self.etree.tostring
3168 self.assertRaises(TypeError, self.etree.tostring,
3169 None, encoding=_unicode)
3170
3172 tostring = self.etree.tostring
3173 Element = self.etree.Element
3174 SubElement = self.etree.SubElement
3175
3176 a = Element('a')
3177 b = SubElement(a, 'b')
3178 c = SubElement(a, 'c')
3179 d = SubElement(c, 'd')
3180 b.tail = 'Foo'
3181
3182 self.assertTrue(isinstance(tostring(b, encoding=_unicode), _unicode))
3183 self.assertTrue(tostring(b, encoding=_unicode) == '<b/>Foo' or
3184 tostring(b, encoding=_unicode) == '<b />Foo')
3185
3187 tostring = self.etree.tostring
3188 Element = self.etree.Element
3189 SubElement = self.etree.SubElement
3190
3191 a = Element('a')
3192 b = SubElement(a, 'b')
3193 c = SubElement(a, 'c')
3194
3195 result = tostring(a, encoding=_unicode)
3196 self.assertEqual(result, "<a><b/><c/></a>")
3197
3198 result = tostring(a, encoding=_unicode, pretty_print=False)
3199 self.assertEqual(result, "<a><b/><c/></a>")
3200
3201 result = tostring(a, encoding=_unicode, pretty_print=True)
3202 self.assertEqual(result, "<a>\n <b/>\n <c/>\n</a>\n")
3203
3205 root = etree.Element('parent')
3206 etree.SubElement(root, 'child')
3207
3208 self.assertEqual(len(root), 1)
3209 self.assertEqual(root[0].tag, 'child')
3210
3211 # in PyPy, GC used to kill the Python proxy instance without cleanup
3212 gc.collect()
3213 self.assertEqual(len(root), 1)
3214 self.assertEqual(root[0].tag, 'child')
3215
3216 # helper methods
3217
3219 """Write out element for comparison.
3220 """
3221 ElementTree = self.etree.ElementTree
3222 f = BytesIO()
3223 tree = ElementTree(element=element)
3224 tree.write(f, encoding=encoding, compression=compression)
3225 data = f.getvalue()
3226 if compression:
3227 data = zlib.decompress(data)
3228 return canonicalize(data)
3229
3230
3233 filename = fileInTestDir('test_broken.xml')
3234 root = etree.XML(_bytes('''\
3235 <doc xmlns:xi="http://www.w3.org/2001/XInclude">
3236 <xi:include href="%s" parse="text"/>
3237 </doc>
3238 ''' % filename))
3239 old_text = root.text
3240 content = read_file(filename)
3241 old_tail = root[0].tail
3242
3243 self.include( etree.ElementTree(root) )
3244 self.assertEqual(old_text + content + old_tail,
3245 root.text)
3246
3248 tree = etree.parse(fileInTestDir('include/test_xinclude.xml'))
3249 self.assertNotEqual(
3250 'a',
3251 tree.getroot()[1].tag)
3252 # process xincludes
3253 self.include( tree )
3254 # check whether we find it replaced with included data
3255 self.assertEqual(
3256 'a',
3257 tree.getroot()[1].tag)
3258
3260 class res(etree.Resolver):
3261 include_text = read_file(fileInTestDir('test.xml'))
3262 called = {}
3263 def resolve(self, url, id, context):
3264 if url.endswith(".dtd"):
3265 self.called["dtd"] = True
3266 return self.resolve_filename(
3267 fileInTestDir('test.dtd'), context)
3268 elif url.endswith("test_xinclude.xml"):
3269 self.called["input"] = True
3270 return None # delegate to default resolver
3271 else:
3272 self.called["include"] = True
3273 return self.resolve_string(self.include_text, context)
3274
3275 res_instance = res()
3276 parser = etree.XMLParser(load_dtd = True)
3277 parser.resolvers.add(res_instance)
3278
3279 tree = etree.parse(fileInTestDir('include/test_xinclude.xml'),
3280 parser = parser)
3281
3282 self.include(tree)
3283
3284 called = list(res_instance.called.items())
3285 called.sort()
3286 self.assertEqual(
3287 [("dtd", True), ("include", True), ("input", True)],
3288 called)
3289
3293
3294
3299
3300
3303 tree = self.parse(_bytes('<a><b/></a>'))
3304 f = BytesIO()
3305 tree.write_c14n(f)
3306 s = f.getvalue()
3307 self.assertEqual(_bytes('<a><b></b></a>'),
3308 s)
3309
3311 tree = self.parse(_bytes('<a>'+'<b/>'*200+'</a>'))
3312 f = BytesIO()
3313 tree.write_c14n(f, compression=9)
3314 gzfile = gzip.GzipFile(fileobj=BytesIO(f.getvalue()))
3315 try:
3316 s = gzfile.read()
3317 finally:
3318 gzfile.close()
3319 self.assertEqual(_bytes('<a>'+'<b></b>'*200+'</a>'),
3320 s)
3321
3323 tree = self.parse(_bytes('<a><b/></a>'))
3324 handle, filename = tempfile.mkstemp()
3325 try:
3326 tree.write_c14n(filename)
3327 data = read_file(filename, 'rb')
3328 finally:
3329 os.close(handle)
3330 os.remove(filename)
3331 self.assertEqual(_bytes('<a><b></b></a>'),
3332 data)
3333
3335 tree = self.parse(_bytes('<a>'+'<b/>'*200+'</a>'))
3336 handle, filename = tempfile.mkstemp()
3337 try:
3338 tree.write_c14n(filename, compression=9)
3339 f = gzip.open(filename, 'rb')
3340 try:
3341 data = f.read()
3342 finally:
3343 f.close()
3344 finally:
3345 os.close(handle)
3346 os.remove(filename)
3347 self.assertEqual(_bytes('<a>'+'<b></b>'*200+'</a>'),
3348 data)
3349
3351 tree = self.parse(_bytes('<!--hi--><a><!--ho--><b/></a><!--hu-->'))
3352 f = BytesIO()
3353 tree.write_c14n(f)
3354 s = f.getvalue()
3355 self.assertEqual(_bytes('<!--hi-->\n<a><!--ho--><b></b></a>\n<!--hu-->'),
3356 s)
3357 f = BytesIO()
3358 tree.write_c14n(f, with_comments=True)
3359 s = f.getvalue()
3360 self.assertEqual(_bytes('<!--hi-->\n<a><!--ho--><b></b></a>\n<!--hu-->'),
3361 s)
3362 f = BytesIO()
3363 tree.write_c14n(f, with_comments=False)
3364 s = f.getvalue()
3365 self.assertEqual(_bytes('<a><b></b></a>'),
3366 s)
3367
3369 tree = self.parse(_bytes('<!--hi--><a><!--ho--><b/></a><!--hu-->'))
3370 s = etree.tostring(tree, method='c14n')
3371 self.assertEqual(_bytes('<!--hi-->\n<a><!--ho--><b></b></a>\n<!--hu-->'),
3372 s)
3373 s = etree.tostring(tree, method='c14n', with_comments=True)
3374 self.assertEqual(_bytes('<!--hi-->\n<a><!--ho--><b></b></a>\n<!--hu-->'),
3375 s)
3376 s = etree.tostring(tree, method='c14n', with_comments=False)
3377 self.assertEqual(_bytes('<a><b></b></a>'),
3378 s)
3379
3381 tree = self.parse(_bytes('<!--hi--><a><!--ho--><b/></a><!--hu-->'))
3382 s = etree.tostring(tree.getroot(), method='c14n')
3383 self.assertEqual(_bytes('<a><!--ho--><b></b></a>'),
3384 s)
3385 s = etree.tostring(tree.getroot(), method='c14n', with_comments=True)
3386 self.assertEqual(_bytes('<a><!--ho--><b></b></a>'),
3387 s)
3388 s = etree.tostring(tree.getroot(), method='c14n', with_comments=False)
3389 self.assertEqual(_bytes('<a><b></b></a>'),
3390 s)
3391
3393 tree = self.parse(_bytes(
3394 '<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b/></a>'))
3395 f = BytesIO()
3396 tree.write_c14n(f)
3397 s = f.getvalue()
3398 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b></z:b></a>'),
3399 s)
3400 f = BytesIO()
3401 tree.write_c14n(f, exclusive=False)
3402 s = f.getvalue()
3403 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b></z:b></a>'),
3404 s)
3405 f = BytesIO()
3406 tree.write_c14n(f, exclusive=True)
3407 s = f.getvalue()
3408 self.assertEqual(_bytes('<a xmlns="http://abc"><z:b xmlns:z="http://cde"></z:b></a>'),
3409 s)
3410
3411 f = BytesIO()
3412 tree.write_c14n(f, exclusive=True, inclusive_ns_prefixes=['z'])
3413 s = f.getvalue()
3414 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:z="http://cde"><z:b></z:b></a>'),
3415 s)
3416
3418 tree = self.parse(_bytes(
3419 '<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b/></a>'))
3420 s = etree.tostring(tree, method='c14n')
3421 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b></z:b></a>'),
3422 s)
3423 s = etree.tostring(tree, method='c14n', exclusive=False)
3424 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b></z:b></a>'),
3425 s)
3426 s = etree.tostring(tree, method='c14n', exclusive=True)
3427 self.assertEqual(_bytes('<a xmlns="http://abc"><z:b xmlns:z="http://cde"></z:b></a>'),
3428 s)
3429
3430 s = etree.tostring(tree, method='c14n', exclusive=True, inclusive_ns_prefixes=['y'])
3431 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:y="http://bcd"><z:b xmlns:z="http://cde"></z:b></a>'),
3432 s)
3433
3435 tree = self.parse(_bytes(
3436 '<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b/></a>'))
3437 s = etree.tostring(tree.getroot(), method='c14n')
3438 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b></z:b></a>'),
3439 s)
3440 s = etree.tostring(tree.getroot(), method='c14n', exclusive=False)
3441 self.assertEqual(_bytes('<a xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b></z:b></a>'),
3442 s)
3443 s = etree.tostring(tree.getroot(), method='c14n', exclusive=True)
3444 self.assertEqual(_bytes('<a xmlns="http://abc"><z:b xmlns:z="http://cde"></z:b></a>'),
3445 s)
3446
3447 s = etree.tostring(tree.getroot()[0], method='c14n', exclusive=False)
3448 self.assertEqual(_bytes('<z:b xmlns="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"></z:b>'),
3449 s)
3450 s = etree.tostring(tree.getroot()[0], method='c14n', exclusive=True)
3451 self.assertEqual(_bytes('<z:b xmlns:z="http://cde"></z:b>'),
3452 s)
3453
3454 s = etree.tostring(tree.getroot()[0], method='c14n', exclusive=True, inclusive_ns_prefixes=['y'])
3455 self.assertEqual(_bytes('<z:b xmlns:y="http://bcd" xmlns:z="http://cde"></z:b>'),
3456 s)
3457
3459 """ Regression test to fix memory allocation issues (use 3+ inclusive NS spaces)"""
3460 tree = self.parse(_bytes(
3461 '<a xmlns:x="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b/></a>'))
3462
3463 s = etree.tostring(tree, method='c14n', exclusive=True, inclusive_ns_prefixes=['x', 'y', 'z'])
3464 self.assertEqual(_bytes('<a xmlns:x="http://abc" xmlns:y="http://bcd" xmlns:z="http://cde"><z:b></z:b></a>'),
3465 s)
3466
3467
3470 tree = self.parse(_bytes('<a><b/></a>'))
3471 f = BytesIO()
3472 tree.write(f)
3473 s = f.getvalue()
3474 self.assertEqual(_bytes('<a><b/></a>'),
3475 s)
3476
3478 tree = self.parse(_bytes('<a>'+'<b/>'*200+'</a>'))
3479 f = BytesIO()
3480 tree.write(f, compression=9)
3481 gzfile = gzip.GzipFile(fileobj=BytesIO(f.getvalue()))
3482 try:
3483 s = gzfile.read()
3484 finally:
3485 gzfile.close()
3486 self.assertEqual(_bytes('<a>'+'<b/>'*200+'</a>'),
3487 s)
3488
3490 tree = self.parse(_bytes('<a>'+'<b/>'*200+'</a>'))
3491 f = BytesIO()
3492 tree.write(f, compression=0)
3493 s0 = f.getvalue()
3494
3495 f = BytesIO()
3496 tree.write(f)
3497 self.assertEqual(f.getvalue(), s0)
3498
3499 f = BytesIO()
3500 tree.write(f, compression=1)
3501 s = f.getvalue()
3502 self.assertTrue(len(s) <= len(s0))
3503 gzfile = gzip.GzipFile(fileobj=BytesIO(s))
3504 try:
3505 s1 = gzfile.read()
3506 finally:
3507 gzfile.close()
3508
3509 f = BytesIO()
3510 tree.write(f, compression=9)
3511 s = f.getvalue()
3512 self.assertTrue(len(s) <= len(s0))
3513 gzfile = gzip.GzipFile(fileobj=BytesIO(s))
3514 try:
3515 s9 = gzfile.read()
3516 finally:
3517 gzfile.close()
3518
3519 self.assertEqual(_bytes('<a>'+'<b/>'*200+'</a>'),
3520 s0)
3521 self.assertEqual(_bytes('<a>'+'<b/>'*200+'</a>'),
3522 s1)
3523 self.assertEqual(_bytes('<a>'+'<b/>'*200+'</a>'),
3524 s9)
3525
3527 tree = self.parse(_bytes('<a><b/></a>'))
3528 handle, filename = tempfile.mkstemp()
3529 try:
3530 tree.write(filename)
3531 data = read_file(filename, 'rb')
3532 finally:
3533 os.close(handle)
3534 os.remove(filename)
3535 self.assertEqual(_bytes('<a><b/></a>'),
3536 data)
3537
3539 tree = self.parse(_bytes('<a>'+'<b/>'*200+'</a>'))
3540 handle, filename = tempfile.mkstemp()
3541 try:
3542 tree.write(filename, compression=9)
3543 f = gzip.open(filename, 'rb')
3544 try:
3545 data = f.read()
3546 finally:
3547 f.close()
3548 finally:
3549 os.close(handle)
3550 os.remove(filename)
3551 self.assertEqual(_bytes('<a>'+'<b/>'*200+'</a>'),
3552 data)
3553
3555 tree = self.parse(_bytes('<a>'+'<b/>'*200+'</a>'))
3556 handle, filename = tempfile.mkstemp()
3557 try:
3558 tree.write(filename, compression=9)
3559 data = etree.tostring(etree.parse(filename))
3560 finally:
3561 os.close(handle)
3562 os.remove(filename)
3563 self.assertEqual(_bytes('<a>'+'<b/>'*200+'</a>'),
3564 data)
3565
3567 tree = self.parse(_bytes('<a>'+'<b/>'*200+'</a>'))
3568 handle, filename = tempfile.mkstemp()
3569 try:
3570 tree.write(filename, compression=9)
3571 data = etree.tostring(etree.parse(
3572 gzip.GzipFile(filename)))
3573 finally:
3574 os.close(handle)
3575 os.remove(filename)
3576 self.assertEqual(_bytes('<a>'+'<b/>'*200+'</a>'),
3577 data)
3578
3580 etree = etree
3581
3583 parse = self.etree.parse
3584 f = BytesIO('<a><b></c></b></a>')
3585 self.etree.clear_error_log()
3586 try:
3587 parse(f)
3588 logs = None
3589 except SyntaxError:
3590 e = sys.exc_info()[1]
3591 logs = e.error_log
3592 f.close()
3593 self.assertTrue([ log for log in logs
3594 if 'mismatch' in log.message ])
3595 self.assertTrue([ log for log in logs
3596 if 'PARSER' in log.domain_name])
3597 self.assertTrue([ log for log in logs
3598 if 'ERR_TAG_NAME_MISMATCH' in log.type_name ])
3599 self.assertTrue([ log for log in logs
3600 if 1 == log.line ])
3601 self.assertTrue([ log for log in logs
3602 if 15 == log.column ])
3603
3614
3615 self.etree.use_global_python_log(Logger())
3616 f = BytesIO('<a><b></c></b></a>')
3617 try:
3618 parse(f)
3619 except SyntaxError:
3620 pass
3621 f.close()
3622
3623 self.assertTrue([ message for message in messages
3624 if 'mismatch' in message ])
3625 self.assertTrue([ message for message in messages
3626 if ':PARSER:' in message])
3627 self.assertTrue([ message for message in messages
3628 if ':ERR_TAG_NAME_MISMATCH:' in message ])
3629 self.assertTrue([ message for message in messages
3630 if ':1:15:' in message ])
3631
3633 suite = unittest.TestSuite()
3634 suite.addTests([unittest.makeSuite(ETreeOnlyTestCase)])
3635 suite.addTests([unittest.makeSuite(ETreeXIncludeTestCase)])
3636 suite.addTests([unittest.makeSuite(ElementIncludeTestCase)])
3637 suite.addTests([unittest.makeSuite(ETreeC14NTestCase)])
3638 suite.addTests([unittest.makeSuite(ETreeWriteTestCase)])
3639 suite.addTests([unittest.makeSuite(ETreeErrorLogTest)])
3640 suite.addTests(
3641 [make_doctest('../../../doc/tutorial.txt')])
3642 if sys.version_info >= (2,6):
3643 # now requires the 'with' statement
3644 suite.addTests(
3645 [make_doctest('../../../doc/api.txt')])
3646 suite.addTests(
3647 [make_doctest('../../../doc/FAQ.txt')])
3648 suite.addTests(
3649 [make_doctest('../../../doc/parsing.txt')])
3650 suite.addTests(
3651 [make_doctest('../../../doc/resolvers.txt')])
3652 return suite
3653
3654 if __name__ == '__main__':
3655 print('to test use test.py %s' % __file__)
3656
| Home | Trees | Indices | Help |
|
|---|
| Generated by Epydoc 3.0.1 on Sun Apr 28 21:00:12 2013 | http://epydoc.sourceforge.net |