Skip to content

Commit 3fd6ada

Browse files
[3.11] bpo-45229: Make ElementTree tests discoverable (GH-108859) (GH-108874)
(cherry picked from commit 074ac1f)
1 parent 723ca8c commit 3fd6ada

File tree

2 files changed

+35
-61
lines changed

2 files changed

+35
-61
lines changed

Lib/test/test_xml_etree.py

Lines changed: 17 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -365,6 +365,7 @@ def test_path_cache(self):
365365
from xml.etree import ElementPath
366366

367367
elem = ET.XML(SAMPLE_XML)
368+
ElementPath._cache.clear()
368369
for i in range(10): ET.ElementTree(elem).find('./'+str(i))
369370
cache_len_10 = len(ElementPath._cache)
370371
for i in range(10): ET.ElementTree(elem).find('./'+str(i))
@@ -3955,8 +3956,9 @@ def test_issue14818(self):
39553956
# --------------------------------------------------------------------
39563957

39573958
class NoAcceleratorTest(unittest.TestCase):
3958-
def setUp(self):
3959-
if not pyET:
3959+
@classmethod
3960+
def setUpClass(cls):
3961+
if ET is not pyET:
39603962
raise unittest.SkipTest('only for the Python version')
39613963

39623964
# Test that the C accelerator was not imported for pyET
@@ -4202,8 +4204,7 @@ def get_option(config, option_name, default=None):
42024204

42034205
# --------------------------------------------------------------------
42044206

4205-
4206-
def test_main(module=None):
4207+
def setUpModule(module=None):
42074208
# When invoked without a module, runs the Python ET tests by loading pyET.
42084209
# Otherwise, uses the given module as the ET.
42094210
global pyET
@@ -4215,62 +4216,30 @@ def test_main(module=None):
42154216
global ET
42164217
ET = module
42174218

4218-
test_classes = [
4219-
ModuleTest,
4220-
ElementSlicingTest,
4221-
BasicElementTest,
4222-
BadElementTest,
4223-
BadElementPathTest,
4224-
ElementTreeTest,
4225-
IOTest,
4226-
ParseErrorTest,
4227-
XIncludeTest,
4228-
ElementTreeTypeTest,
4229-
ElementFindTest,
4230-
ElementIterTest,
4231-
TreeBuilderTest,
4232-
XMLParserTest,
4233-
XMLPullParserTest,
4234-
BugsTest,
4235-
KeywordArgsTest,
4236-
C14NTest,
4237-
]
4238-
4239-
# These tests will only run for the pure-Python version that doesn't import
4240-
# _elementtree. We can't use skipUnless here, because pyET is filled in only
4241-
# after the module is loaded.
4242-
if pyET is not ET:
4243-
test_classes.extend([
4244-
NoAcceleratorTest,
4245-
])
4219+
# don't interfere with subsequent tests
4220+
def cleanup():
4221+
global ET, pyET
4222+
ET = pyET = None
4223+
unittest.addModuleCleanup(cleanup)
42464224

42474225
# Provide default namespace mapping and path cache.
42484226
from xml.etree import ElementPath
42494227
nsmap = ET.register_namespace._namespace_map
42504228
# Copy the default namespace mapping
42514229
nsmap_copy = nsmap.copy()
4230+
unittest.addModuleCleanup(nsmap.update, nsmap_copy)
4231+
unittest.addModuleCleanup(nsmap.clear)
4232+
42524233
# Copy the path cache (should be empty)
42534234
path_cache = ElementPath._cache
4235+
unittest.addModuleCleanup(setattr, ElementPath, "_cache", path_cache)
42544236
ElementPath._cache = path_cache.copy()
4237+
42554238
# Align the Comment/PI factories.
42564239
if hasattr(ET, '_set_factories'):
42574240
old_factories = ET._set_factories(ET.Comment, ET.PI)
4258-
else:
4259-
old_factories = None
4260-
4261-
try:
4262-
return support.run_unittest(*test_classes)
4263-
finally:
4264-
from xml.etree import ElementPath
4265-
# Restore mapping and path cache
4266-
nsmap.clear()
4267-
nsmap.update(nsmap_copy)
4268-
ElementPath._cache = path_cache
4269-
if old_factories is not None:
4270-
ET._set_factories(*old_factories)
4271-
# don't interfere with subsequent tests
4272-
ET = pyET = None
4241+
unittest.addModuleCleanup(ET._set_factories, *old_factories)
42734242

42744243

42754244
if __name__ == '__main__':
4276-
test_main()
4245+
unittest.main()

Lib/test/test_xml_etree_c.py

Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -234,20 +234,25 @@ def test_element_with_children(self):
234234
self.check_sizeof(e, self.elementsize + self.extra +
235235
struct.calcsize('8P'))
236236

237-
def test_main():
238-
from test import test_xml_etree
239-
240-
# Run the tests specific to the C implementation
241-
support.run_unittest(
242-
MiscTests,
243-
TestAliasWorking,
244-
TestAcceleratorImported,
245-
SizeofTest,
246-
)
247237

248-
# Run the same test suite as the Python module
249-
test_xml_etree.test_main(module=cET)
238+
def install_tests():
239+
# Test classes should have __module__ referring to this module.
240+
from test import test_xml_etree
241+
for name, base in vars(test_xml_etree).items():
242+
if isinstance(base, type) and issubclass(base, unittest.TestCase):
243+
class Temp(base):
244+
pass
245+
Temp.__name__ = Temp.__qualname__ = name
246+
Temp.__module__ = __name__
247+
assert name not in globals()
248+
globals()[name] = Temp
249+
250+
install_tests()
251+
252+
def setUpModule():
253+
from test import test_xml_etree
254+
test_xml_etree.setUpModule(module=cET)
250255

251256

252257
if __name__ == '__main__':
253-
test_main()
258+
unittest.main()

0 commit comments

Comments
 (0)