ansible-test - Upgrade coverage for Python 3.10+ (#86811)

* Upgrade coverage for Python 3.10+.
* Fix unit tests.
* Use ctrace to improve performance. It's unclear why this improves performance on Python 3.10 and 3.14.
pull/86819/head
Matt Clay 1 month ago committed by GitHub
parent efb9446769
commit a712f79bf1
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -0,0 +1,2 @@
minor_changes:
- ansible-test - Upgrade ``coverage`` for Python 3.10 and later.

@ -1,2 +1,3 @@
# The test-constraints sanity test verifies this file, but changes must be made manually to keep it in up-to-date.
coverage == 7.10.7 ; python_version >= '3.9' and python_version <= '3.14'
coverage == 7.13.5 ; python_version >= '3.10' and python_version <= '3.15'
coverage == 7.10.7 ; python_version >= '3.9' and python_version <= '3.9'

@ -69,7 +69,8 @@ class CoverageVersion:
COVERAGE_VERSIONS = (
# IMPORTANT: Keep this in sync with the ansible-test.txt requirements file.
CoverageVersion('7.10.7', 7, (3, 9), (3, 14)),
CoverageVersion('7.13.5', 7, (3, 10), (3, 15)),
CoverageVersion('7.10.7', 7, (3, 9), (3, 9)),
)
"""
This tuple specifies the coverage version to use for Python version ranges.
@ -248,6 +249,7 @@ def generate_ansible_coverage_config() -> str:
"""Generate code coverage configuration for Ansible tests."""
coverage_config = """
[run]
core = ctrace
branch = True
concurrency =
multiprocessing
@ -288,6 +290,7 @@ def generate_collection_coverage_config() -> str:
coverage_config = f"""
[run]
core = ctrace
branch = True
concurrency =
multiprocessing

@ -22,41 +22,51 @@ class TestImports(unittest.TestCase):
if mod in sys.modules:
del sys.modules[mod]
@patch.object(builtins, '__import__')
def test_module_utils_basic_import_syslog(self, mock_import):
def test_module_utils_basic_import_syslog(self):
present = True
def _mock_import(name, *args, **kwargs):
if name == 'syslog':
if present:
return unittest.mock.MagicMock()
raise ImportError
return realimport(name, *args, **kwargs)
self.clear_modules(['syslog', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertTrue(mod.module_utils.basic.HAS_SYSLOG)
with patch.object(builtins, '__import__', _mock_import):
self.clear_modules(['syslog', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertTrue(mod.module_utils.basic.HAS_SYSLOG)
present = False
self.clear_modules(['syslog', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertFalse(mod.module_utils.basic.HAS_SYSLOG)
self.clear_modules(['syslog', 'ansible.module_utils.basic'])
self.clear_modules(['syslog', 'ansible.module_utils.basic'])
mock_import.side_effect = _mock_import
mod = builtins.__import__('ansible.module_utils.basic')
self.assertFalse(mod.module_utils.basic.HAS_SYSLOG)
def test_module_utils_basic_import_selinux(self):
present = True
@patch.object(builtins, '__import__')
def test_module_utils_basic_import_selinux(self, mock_import):
def _mock_import(name, globals=None, locals=None, fromlist=tuple(), level=0, **kwargs):
if name == 'ansible.module_utils.compat' and fromlist == ('selinux',):
if present:
return unittest.mock.MagicMock()
raise ImportError
return realimport(name, globals=globals, locals=locals, fromlist=fromlist, level=level, **kwargs)
try:
with patch.object(builtins, '__import__', _mock_import):
self.clear_modules(['ansible.module_utils.compat.selinux', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertTrue(mod.module_utils.basic.HAVE_SELINUX)
except ImportError:
# no selinux on test system, so skip
pass
self.clear_modules(['ansible.module_utils.compat.selinux', 'ansible.module_utils.basic'])
mock_import.side_effect = _mock_import
mod = builtins.__import__('ansible.module_utils.basic')
self.assertFalse(mod.module_utils.basic.HAVE_SELINUX)
present = False
self.clear_modules(['ansible.module_utils.compat.selinux', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertFalse(mod.module_utils.basic.HAVE_SELINUX)
self.clear_modules(['ansible.module_utils.compat.selinux', 'ansible.module_utils.basic'])
# FIXME: doesn't work yet
# @patch.object(builtins, 'bytes')
@ -64,22 +74,29 @@ class TestImports(unittest.TestCase):
# mock_bytes.side_effect = NameError()
# from ansible.module_utils import basic
@patch.object(builtins, '__import__')
def test_module_utils_basic_import_systemd_journal(self, mock_import):
def test_module_utils_basic_import_systemd_journal(self):
present = True
def _mock_import(name, *args, **kwargs):
try:
fromlist = kwargs.get('fromlist', args[2])
except IndexError:
fromlist = []
if name == 'systemd' and 'journal' in fromlist:
if present:
return unittest.mock.MagicMock()
raise ImportError
return realimport(name, *args, **kwargs)
self.clear_modules(['systemd', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertTrue(mod.module_utils.basic.has_journal)
with patch.object(builtins, '__import__', _mock_import):
self.clear_modules(['systemd', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertTrue(mod.module_utils.basic.has_journal)
present = False
self.clear_modules(['systemd', 'ansible.module_utils.basic'])
mod = builtins.__import__('ansible.module_utils.basic')
self.assertFalse(mod.module_utils.basic.has_journal)
self.clear_modules(['systemd', 'ansible.module_utils.basic'])
mock_import.side_effect = _mock_import
mod = builtins.__import__('ansible.module_utils.basic')
self.assertFalse(mod.module_utils.basic.has_journal)
self.clear_modules(['systemd', 'ansible.module_utils.basic'])

@ -19,6 +19,7 @@
from __future__ import annotations
import os
import sys
import unittest
from unittest.mock import patch, MagicMock
@ -49,10 +50,12 @@ class TestErrors(unittest.TestCase):
bam = MagicMock()
bam.__file__ = '/path/to/my/foo/bar/bam/__init__.py'
bar_pkg.bam = bam
foo_pkg.return_value.bar = bar_pkg
foo_pkg.bar = bar_pkg
pl = PluginLoader('test', 'foo.bar.bam', 'test', 'test_plugin')
with patch('builtins.__import__', foo_pkg):
self.assertEqual(pl._get_package_paths(), ['/path/to/my/foo/bar/bam'])
sys.modules['foo'] = foo_pkg
sys.modules['foo.bar'] = bar_pkg
sys.modules['foo.bar.bam'] = bam
self.assertEqual(pl._get_package_paths(), ['/path/to/my/foo/bar/bam'])
def test_plugins__get_paths(self):
pl = PluginLoader('test', '', 'test', 'test_plugin')

Loading…
Cancel
Save