From 5d294f15de92d40aa690717a96f9001f395ede04 Mon Sep 17 00:00:00 2001 From: Henry Schreiner Date: Sun, 19 May 2024 00:10:46 -0400 Subject: [PATCH 1/3] fix: support noxfile being a symlink Signed-off-by: Henry Schreiner --- nox/tasks.py | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/nox/tasks.py b/nox/tasks.py index e2576416..62bee9b5 100644 --- a/nox/tasks.py +++ b/nox/tasks.py @@ -83,13 +83,15 @@ def load_nox_module(global_config: Namespace) -> types.ModuleType | int: # Be sure to expand variables global_config_noxfile = os.path.expandvars(global_config.noxfile) + # Make sure we only expand the parent dir just in case the noxfile is a symlink + noxfile_parent_dir = os.path.realpath(os.path.dirname(global_config_noxfile)) + # Save the absolute path to the Noxfile. # This will inoculate it if Nox changes paths because of an implicit # or explicit chdir (like the one below). - global_config.noxfile = os.path.realpath(global_config_noxfile) - - # Make sure we only expand the parent dir just in case the noxfile is a symlink - noxfile_parent_dir = os.path.realpath(os.path.dirname(global_config.noxfile)) + global_config.noxfile = os.path.join( + noxfile_parent_dir, os.path.basename(global_config_noxfile) + ) try: # Check ``nox.needs_version`` by parsing the AST. From b4aa701d9a536d4ea474d63fc2f0439e96719ce9 Mon Sep 17 00:00:00 2001 From: Henry Schreiner Date: Fri, 1 Nov 2024 18:22:26 -0400 Subject: [PATCH 2/3] feat: add session.noxfile and add tests Signed-off-by: Henry Schreiner --- nox/sessions.py | 10 ++++++++++ tests/resources/orig_dir/noxfile.py | 17 +++++++++++++++++ tests/resources/orig_dir/orig_file.txt | 0 tests/resources/sym_dir/noxfile.py | 1 + tests/resources/sym_dir/sym_file.txt | 0 tests/test_main.py | 23 +++++++++++++++++++++++ 6 files changed, 51 insertions(+) create mode 100644 tests/resources/orig_dir/noxfile.py create mode 100644 tests/resources/orig_dir/orig_file.txt create mode 120000 tests/resources/sym_dir/noxfile.py create mode 100644 tests/resources/sym_dir/sym_file.txt diff --git a/nox/sessions.py b/nox/sessions.py index 3a51d751..eff91a82 100644 --- a/nox/sessions.py +++ b/nox/sessions.py @@ -198,6 +198,16 @@ def virtualenv(self) -> ProcessEnv: raise ValueError("A virtualenv has not been created for this session") return venv + @property + def noxfile(self) -> pathlib.Path: + """The path to the Noxfile that defines this session. + + If the noxfile is a symlink, this does not resolve that last symlink; it + has been resolved up to that point. Use `session.noxfile.resolve()` to + get the original file path. + """ + return pathlib.Path(self._runner.global_config.noxfile) + @property def venv_backend(self) -> str: """The venv_backend selected.""" diff --git a/tests/resources/orig_dir/noxfile.py b/tests/resources/orig_dir/noxfile.py new file mode 100644 index 00000000..f58a7f22 --- /dev/null +++ b/tests/resources/orig_dir/noxfile.py @@ -0,0 +1,17 @@ +from pathlib import Path + +import nox + +DIR = Path(__file__).parent.resolve() + + +@nox.session(venv_backend="none", default=False) +def orig(session: nox.Session) -> None: + assert Path("orig_file.txt").exists() + + +@nox.session(venv_backend="none", default=False) +def sym(session: nox.Session) -> None: + assert Path("sym_file.txt").exists() + + assert session.noxfile.resolve().parent.joinpath("orig_file.txt").exists() diff --git a/tests/resources/orig_dir/orig_file.txt b/tests/resources/orig_dir/orig_file.txt new file mode 100644 index 00000000..e69de29b diff --git a/tests/resources/sym_dir/noxfile.py b/tests/resources/sym_dir/noxfile.py new file mode 120000 index 00000000..67bd5e2c --- /dev/null +++ b/tests/resources/sym_dir/noxfile.py @@ -0,0 +1 @@ +../orig_dir/noxfile.py \ No newline at end of file diff --git a/tests/resources/sym_dir/sym_file.txt b/tests/resources/sym_dir/sym_file.txt new file mode 100644 index 00000000..e69de29b diff --git a/tests/test_main.py b/tests/test_main.py index 0cb737a8..72bbe755 100644 --- a/tests/test_main.py +++ b/tests/test_main.py @@ -16,6 +16,7 @@ import contextlib import os +import subprocess import sys from importlib import metadata from pathlib import Path @@ -928,3 +929,25 @@ def test_noxfile_options_cant_be_set(): def test_noxfile_options_cant_be_set_long(): with pytest.raises(AttributeError, match="i_am_clearly_not_an_option"): nox.options.i_am_clearly_not_an_option = True + + +def test_symlink_orig(monkeypatch): + monkeypatch.chdir(Path(RESOURCES) / "orig_dir") + subprocess.run([sys.executable, "-m", "nox", "-s", "orig"], check=True) + + +def test_symlink_orig_not(monkeypatch): + monkeypatch.chdir(Path(RESOURCES) / "orig_dir") + res = subprocess.run([sys.executable, "-m", "nox", "-s", "sym"], check=False) + assert res.returncode == 1 + + +def test_symlink_sym(monkeypatch): + monkeypatch.chdir(Path(RESOURCES) / "sym_dir") + subprocess.run([sys.executable, "-m", "nox", "-s", "sym"], check=True) + + +def test_symlink_sym_not(monkeypatch): + monkeypatch.chdir(Path(RESOURCES) / "sym_dir") + res = subprocess.run([sys.executable, "-m", "nox", "-s", "orig"], check=False) + assert res.returncode == 1 From ffeb9df5a9a83140c4741c5294a5b5efb8ee357c Mon Sep 17 00:00:00 2001 From: Henry Schreiner Date: Fri, 1 Nov 2024 23:04:32 -0400 Subject: [PATCH 3/3] refactor: remove session.noxfile in prefernce for __path__ Signed-off-by: Henry Schreiner --- nox/sessions.py | 10 ---------- tests/resources/orig_dir/noxfile.py | 4 ++-- 2 files changed, 2 insertions(+), 12 deletions(-) diff --git a/nox/sessions.py b/nox/sessions.py index eff91a82..3a51d751 100644 --- a/nox/sessions.py +++ b/nox/sessions.py @@ -198,16 +198,6 @@ def virtualenv(self) -> ProcessEnv: raise ValueError("A virtualenv has not been created for this session") return venv - @property - def noxfile(self) -> pathlib.Path: - """The path to the Noxfile that defines this session. - - If the noxfile is a symlink, this does not resolve that last symlink; it - has been resolved up to that point. Use `session.noxfile.resolve()` to - get the original file path. - """ - return pathlib.Path(self._runner.global_config.noxfile) - @property def venv_backend(self) -> str: """The venv_backend selected.""" diff --git a/tests/resources/orig_dir/noxfile.py b/tests/resources/orig_dir/noxfile.py index f58a7f22..f6eb8ab6 100644 --- a/tests/resources/orig_dir/noxfile.py +++ b/tests/resources/orig_dir/noxfile.py @@ -2,7 +2,7 @@ import nox -DIR = Path(__file__).parent.resolve() +FILE = Path(__file__).resolve() @nox.session(venv_backend="none", default=False) @@ -14,4 +14,4 @@ def orig(session: nox.Session) -> None: def sym(session: nox.Session) -> None: assert Path("sym_file.txt").exists() - assert session.noxfile.resolve().parent.joinpath("orig_file.txt").exists() + assert FILE.parent.joinpath("orig_file.txt").exists()