From 6051a0847c6c1b19002354e445d9acad4db21910 Mon Sep 17 00:00:00 2001 From: Pedro Algarvio Date: Thu, 10 Aug 2023 08:35:57 +0100 Subject: [PATCH] `salt-pip` now properly errors out when being called from a non `onedir` environment. Fixes #64249 Signed-off-by: Pedro Algarvio --- changelog/64249.fixed.md | 1 + salt/scripts.py | 22 +++++++++++-- tests/pytests/functional/cli/test_salt_pip.py | 31 +++++++++++++++++++ 3 files changed, 51 insertions(+), 3 deletions(-) create mode 100644 changelog/64249.fixed.md create mode 100644 tests/pytests/functional/cli/test_salt_pip.py diff --git a/changelog/64249.fixed.md b/changelog/64249.fixed.md new file mode 100644 index 000000000000..9f01a6146cb3 --- /dev/null +++ b/changelog/64249.fixed.md @@ -0,0 +1 @@ +`salt-pip` now properly errors out when being called from a non `onedir` environment. diff --git a/salt/scripts.py b/salt/scripts.py index 07393373c9d6..176cab56366b 100644 --- a/salt/scripts.py +++ b/salt/scripts.py @@ -1,8 +1,7 @@ """ This module contains the function calls to execute command line scripts """ - - +import contextlib import functools import logging import os @@ -608,11 +607,28 @@ def _pip_environment(env, extras): return new_env +def _get_onedir_env_path(): + # This function only exists to simplify testing. + with contextlib.suppress(AttributeError): + return sys.RELENV + return None + + def salt_pip(): """ Proxy to current python's pip """ - extras = str(sys.RELENV / "extras-{}.{}".format(*sys.version_info)) + relenv_path = _get_onedir_env_path() + if relenv_path is None: + print( + "'salt-pip' is only meant to be used from a Salt onedir. You probably " + "want to use the system 'pip` binary.", + file=sys.stderr, + flush=True, + ) + sys.exit(salt.defaults.exitcodes.EX_GENERIC) + else: + extras = str(relenv_path / "extras-{}.{}".format(*sys.version_info)) env = _pip_environment(os.environ.copy(), extras) args = _pip_args(sys.argv[1:], extras) command = [ diff --git a/tests/pytests/functional/cli/test_salt_pip.py b/tests/pytests/functional/cli/test_salt_pip.py new file mode 100644 index 000000000000..22284d8488a4 --- /dev/null +++ b/tests/pytests/functional/cli/test_salt_pip.py @@ -0,0 +1,31 @@ +import os + +import pytest + +import salt.scripts +import salt.utils.platform +from tests.conftest import CODE_DIR +from tests.support.mock import patch + + +def test_within_onedir_env(shell): + if os.environ.get("ONEDIR_TESTRUN", "0") == "0": + return + + script_name = "salt-pip" + if salt.utils.platform.is_windows(): + script_name += ".exe" + + script_path = CODE_DIR / "artifacts" / "salt" / script_name + assert script_path.exists() + + ret = shell.run(str(script_path), "list") + assert ret.returncode == 0 + + +def test_outside_onedir_env(capsys): + with patch("salt.scripts._get_onedir_env_path", return_value=None): + with pytest.raises(SystemExit) as exc: + salt.scripts.salt_pip() + captured = capsys.readouterr() + assert "'salt-pip' is only meant to be used from a Salt onedir." in captured.err