summaryrefslogtreecommitdiff
path: root/test/lib/ansible_test/_data/pytest
diff options
context:
space:
mode:
authorMatt Clay <matt@mystile.com>2019-08-06 14:43:29 -0700
committerGitHub <noreply@github.com>2019-08-06 14:43:29 -0700
commitd651bda12390e46c85c4487859f030ed8851867a (patch)
tree4dbe51c6df169557e342938f6fe3f3632d2dc4a8 /test/lib/ansible_test/_data/pytest
parent923e21836b1a4fb91aa6e93463efe0aea4022144 (diff)
downloadansible-d651bda12390e46c85c4487859f030ed8851867a.tar.gz
Relocate ansible-test code. (#60147)
* Initial move of `test/runner/` content. `test/runner/lib/` -> `test/lib/ansible_test/_internal/` `test/runner/` -> `test/lib/ansible_test/_internal/data/` * Initial move of `test/sanity/` content. `test/sanity/` -> `test/lib/ansible_test/_internal/data/sanity/` (except `test/sanity/ignore.txt`) * Initial move of `test/units/pytest/` content. `test/units/pytest/` -> `test/lib/ansible_test/_internal/data/pytest/` * Follow-up move of `test/runner/unit/` content. `test/lib/ansible_test/_internal/data/unit/` -> `test/lib/ansible_test/tests/unit/` * Initial move of `ansible.cfg` content. `test/units/ansible.cfg` -> `test/lib/ansible_test/_internal/data/units/ansible.cfg` `test/env/ansible.cfg` -> `test/lib/ansible_test/_internal/data/env/ansible.cfg` * Follow-up move of `data` directory. `test/lib/ansible_test/_internal/data/` -> `test/lib/ansible_test/_data/` * Update import statements. * Add missing __init__.py for unit tests. * Fix path references and miscellaneous issues.
Diffstat (limited to 'test/lib/ansible_test/_data/pytest')
-rw-r--r--test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_collections.py34
-rw-r--r--test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_coverage.py59
2 files changed, 93 insertions, 0 deletions
diff --git a/test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_collections.py b/test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_collections.py
new file mode 100644
index 0000000000..ae87187b83
--- /dev/null
+++ b/test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_collections.py
@@ -0,0 +1,34 @@
+"""Enable unit testing of Ansible collections."""
+from __future__ import (absolute_import, division, print_function)
+__metaclass__ = type
+
+import os
+import sys
+
+# set by ansible-test to a single directory, rather than a list of directories as supported by Ansible itself
+ANSIBLE_COLLECTIONS_PATH = os.path.join(os.environ['ANSIBLE_COLLECTIONS_PATHS'], 'ansible_collections')
+
+
+def collection_pypkgpath(self):
+ """Configure the Python package path so that pytest can find our collections."""
+ for parent in self.parts(reverse=True):
+ if str(parent) == ANSIBLE_COLLECTIONS_PATH:
+ return parent
+
+ raise Exception('File "%s" not found in collection path "%s".' % (self.strpath, ANSIBLE_COLLECTIONS_PATH))
+
+
+def pytest_configure():
+ """Configure this pytest plugin."""
+ from ansible.utils.collection_loader import AnsibleCollectionLoader
+
+ # allow unit tests to import code from collections
+ sys.meta_path.insert(0, AnsibleCollectionLoader())
+
+ # noinspection PyProtectedMember
+ import py._path.local
+
+ # force collections unit tests to be loaded with the ansible_collections namespace
+ # original idea from https://stackoverflow.com/questions/50174130/how-do-i-pytest-a-project-using-pep-420-namespace-packages/50175552#50175552
+ # noinspection PyProtectedMember
+ py._path.local.LocalPath.pypkgpath = collection_pypkgpath # pylint: disable=protected-access
diff --git a/test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_coverage.py b/test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_coverage.py
new file mode 100644
index 0000000000..344a091e1c
--- /dev/null
+++ b/test/lib/ansible_test/_data/pytest/plugins/ansible_pytest_coverage.py
@@ -0,0 +1,59 @@
+"""Monkey patch os._exit when running under coverage so we don't lose coverage data in forks, such as with `pytest --boxed`."""
+from __future__ import (absolute_import, division, print_function)
+__metaclass__ = type
+
+
+def pytest_configure():
+ """Configure this pytest plugin."""
+ try:
+ import coverage
+ except ImportError:
+ coverage = None
+
+ try:
+ coverage.Coverage
+ except AttributeError:
+ coverage = None
+
+ if not coverage:
+ return
+
+ import gc
+ import os
+
+ coverage_instances = []
+
+ for obj in gc.get_objects():
+ if isinstance(obj, coverage.Coverage):
+ coverage_instances.append(obj)
+
+ if not coverage_instances:
+ coverage_config = os.environ.get('COVERAGE_CONF')
+
+ if not coverage_config:
+ return
+
+ coverage_output = os.environ.get('COVERAGE_FILE')
+
+ if not coverage_output:
+ return
+
+ cov = coverage.Coverage(config_file=coverage_config)
+ coverage_instances.append(cov)
+ else:
+ cov = None
+
+ # noinspection PyProtectedMember
+ os_exit = os._exit # pylint: disable=protected-access
+
+ def coverage_exit(*args, **kwargs):
+ for instance in coverage_instances:
+ instance.stop()
+ instance.save()
+
+ os_exit(*args, **kwargs)
+
+ os._exit = coverage_exit # pylint: disable=protected-access
+
+ if cov:
+ cov.start()