diff --git a/doc/changes/unreleased.md b/doc/changes/unreleased.md index 6f88b33b7..610e9056c 100644 --- a/doc/changes/unreleased.md +++ b/doc/changes/unreleased.md @@ -12,3 +12,7 @@ * #785: Removed nox session `project:report` and metrics-schema, as superseded by Sonar usage * #763: Parsed and manipulated Changes Files * #788: Removed tbx workflow CLI commands, as superseded by nox session `workflow:generate` + +## Bugfix + +* #798: Added test to ensure `tbx security cve` works diff --git a/test/integration/security_issues_test.py b/test/integration/security_issues_test.py new file mode 100644 index 000000000..a8438fde4 --- /dev/null +++ b/test/integration/security_issues_test.py @@ -0,0 +1,93 @@ +import os +import shutil +import site +import subprocess +from pathlib import Path + +from noxconfig import PROJECT_CONFIG + + +def set_venv_env(monkeypatch, test_path: Path) -> None: + venv_bin = test_path / "venv" / "bin" + monkeypatch.setenv("VIRTUAL_ENV", str(test_path / "venv")) + monkeypatch.setenv("PATH", f"{venv_bin}{os.pathsep}{os.environ['PATH']}") + monkeypatch.setenv("PYTHONPATH", os.pathsep.join(site.getsitepackages())) + + +def test_security_issues_works(tmp_path, monkeypatch): + """ + To ensure that the `tbx security cve` CLI commands work for Java and + other non-Python projects, this test was created which: + - builds a wheel of the python-toolbox + - installs the wheel in a temporary directory + - executes `tbx security cve -- help` to ensure that no errors occur + + This issue primarily arises when one of the modules in `tools` imports something + from `noxconfig`, which is used in the Python projects using the toolbox, but it + is not needed nor used in the non-Python projects. + """ + build_output = subprocess.run(["poetry", "build", "--output", tmp_path]) + assert build_output.returncode == 0 + + venv_output = subprocess.run(["python", "-m", "venv", "venv"], cwd=tmp_path) + assert venv_output.returncode == 0 + + set_venv_env(monkeypatch, tmp_path) + wheel = min(tmp_path.glob("exasol_toolbox-*.whl")) + pip_output = subprocess.run( + ["pip", "install", "--no-deps", str(wheel)], cwd=tmp_path + ) + assert pip_output.returncode == 0 + + tbx_output = subprocess.run(["tbx", "security", "cve", "--help"], cwd=tmp_path) + assert tbx_output.returncode == 0 + + +def test_security_issues_fails_when_imports_noxconfig(tmp_path, monkeypatch): + """ + Reproduces the failure mode where a toolbox runtime module imports + `noxconfig`, which is not available in non-Python projects. + """ + source_root = PROJECT_CONFIG.root_path + project_copy = tmp_path / "python-toolbox-copy" + shutil.copytree( + source_root, + project_copy, + ignore=shutil.ignore_patterns( + ".git", ".venv", "dist", "__pycache__", ".pytest_cache" + ), + ) + + security_py = project_copy / "exasol" / "toolbox" / "tools" / "security.py" + security_text = security_py.read_text() + security_py.write_text( + security_text.replace( + "from __future__ import annotations\n", + "from __future__ import annotations\n\nfrom noxconfig import PROJECT_CONFIG\n", + 1, + ) + ) + + build_output = subprocess.run( + ["poetry", "build", "--output", tmp_path], cwd=project_copy + ) + assert build_output.returncode == 0 + + venv_output = subprocess.run(["python", "-m", "venv", "venv"], cwd=tmp_path) + assert venv_output.returncode == 0 + + set_venv_env(monkeypatch, tmp_path) + wheel = min(tmp_path.glob("exasol_toolbox-*.whl")) + pip_output = subprocess.run( + ["pip", "install", "--no-deps", str(wheel)], cwd=tmp_path + ) + assert pip_output.returncode == 0 + + tbx_output = subprocess.run( + ["tbx", "security", "cve", "--help"], + cwd=tmp_path, + capture_output=True, + text=True, + ) + assert tbx_output.returncode != 0 + assert "No module named 'noxconfig'" in tbx_output.stderr