From b92d026e73eaa27f0016fd1e5658769b00fd62f3 Mon Sep 17 00:00:00 2001 From: James Lamb Date: Mon, 13 May 2024 12:55:39 -0500 Subject: [PATCH] fix: support rendering nested pyproject.toml outputs to stdout (#86) --- .../_rapids_dependency_file_generator.py | 19 +++++++------ .../nested-pyproject/dependencies.yaml | 24 +++++++++++++++++ .../examples/nested-pyproject/pyproject.toml | 2 ++ .../some/cool/code/pyproject.toml | 7 +++++ .../test_rapids_dependency_file_generator.py | 27 +++++++++++++++++++ 5 files changed, 71 insertions(+), 8 deletions(-) create mode 100644 tests/examples/nested-pyproject/dependencies.yaml create mode 100644 tests/examples/nested-pyproject/pyproject.toml create mode 100644 tests/examples/nested-pyproject/some/cool/code/pyproject.toml diff --git a/src/rapids_dependency_file_generator/_rapids_dependency_file_generator.py b/src/rapids_dependency_file_generator/_rapids_dependency_file_generator.py index 96d99316..724b8ee0 100644 --- a/src/rapids_dependency_file_generator/_rapids_dependency_file_generator.py +++ b/src/rapids_dependency_file_generator/_rapids_dependency_file_generator.py @@ -244,8 +244,8 @@ def get_filename(file_type: _config.Output, file_key: str, matrix_combo: dict[st return filename + file_ext -def get_output_dir(file_type: _config.Output, config_file_path: os.PathLike, file_config: _config.File): - """Get the directory to which to write a generated dependency file. +def get_output_dir(*, file_type: _config.Output, config_file_path: os.PathLike, file_config: _config.File): + """Get the directory containing a generated dependency file's contents. The output directory is determined by the `file_type` and the corresponding key in the `file_config`. The path provided in `file_config` will be taken @@ -255,17 +255,16 @@ def get_output_dir(file_type: _config.Output, config_file_path: os.PathLike, fil ---------- file_type : Output An Output value used to determine the file type. - output_root : PathLike - The path to the root directory where dependency files are placed. + config_file_path : PathLike + Path to the dependency-file-generator config file (e.g. dependencies.yaml). file_config : File A dictionary corresponding to one of the [files.$FILENAME] sections of - the dependencies.yaml file. May contain `conda_dir` or - `requirements_dir`. + the dependencies.yaml file. May contain `conda_dir`, `pyproject_dir`, or `requirements_dir`. Returns ------- str - The directory to write the file to. + The directory containing the dependency file's contents. """ path = [os.path.dirname(config_file_path)] if file_type == _config.Output.CONDA: @@ -415,7 +414,11 @@ def make_dependency_files( full_file_name = get_filename(file_type, file_key, matrix_combo) deduped_deps = dedupe(dependencies) - output_dir = "." if to_stdout else get_output_dir(file_type, parsed_config.path, file_config) + output_dir = get_output_dir( + file_type=file_type, + config_file_path=parsed_config.path, + file_config=file_config, + ) contents = make_dependency_file( file_type=file_type, name=full_file_name, diff --git a/tests/examples/nested-pyproject/dependencies.yaml b/tests/examples/nested-pyproject/dependencies.yaml new file mode 100644 index 00000000..5386b14a --- /dev/null +++ b/tests/examples/nested-pyproject/dependencies.yaml @@ -0,0 +1,24 @@ +files: + sparkly_unicorn: + output: pyproject + includes: + - run_deps + extras: + table: project + pyproject_dir: some/cool/code +dependencies: + run_deps: + common: + - output_types: [pyproject] + packages: + - fsspec>=0.6.0 + specific: + - output_types: [pyproject] + matrices: + - matrix: {"cuda": "100.*"} + packages: + - cuda-python>=100.1,<101.0a0 + - matrix: {"cuda": "11.*"} + packages: + - cuda-python>=11.7.1,<12.0a0 + - {matrix: null, packages: ["should-not-be-found-by-test"]} diff --git a/tests/examples/nested-pyproject/pyproject.toml b/tests/examples/nested-pyproject/pyproject.toml new file mode 100644 index 00000000..22ff89f7 --- /dev/null +++ b/tests/examples/nested-pyproject/pyproject.toml @@ -0,0 +1,2 @@ +[tool.some-nonsense] +should_dfg_update_this = "no" diff --git a/tests/examples/nested-pyproject/some/cool/code/pyproject.toml b/tests/examples/nested-pyproject/some/cool/code/pyproject.toml new file mode 100644 index 00000000..5119e180 --- /dev/null +++ b/tests/examples/nested-pyproject/some/cool/code/pyproject.toml @@ -0,0 +1,7 @@ +[project] +name = "beep-boop" +version = "1.2.3" +dependencies = [ + "fsspec>=0.6.0", + "should-not-be-found-by-test", +] # This list was generated by `rapids-dependency-file-generator`. To make changes, edit ../../../dependencies.yaml and run `rapids-dependency-file-generator`. diff --git a/tests/test_rapids_dependency_file_generator.py b/tests/test_rapids_dependency_file_generator.py index 1a35a4e9..2f34a40a 100644 --- a/tests/test_rapids_dependency_file_generator.py +++ b/tests/test_rapids_dependency_file_generator.py @@ -1,12 +1,15 @@ from unittest import mock import yaml +import tomlkit +import pathlib from rapids_dependency_file_generator import _config from rapids_dependency_file_generator._constants import cli_name from rapids_dependency_file_generator._rapids_dependency_file_generator import ( dedupe, make_dependency_file, + make_dependency_files, should_use_specific_entry, ) @@ -67,6 +70,30 @@ def test_make_dependency_file(mock_relpath): assert env == header + "dep1\ndep2\n" +def test_make_dependency_files_should_choose_correct_pyproject_toml(capsys): + + current_dir = pathlib.Path(__file__).parent + make_dependency_files( + parsed_config=_config.load_config_from_file(current_dir / "examples" / "nested-pyproject" / "dependencies.yaml"), + file_keys=["sparkly_unicorn"], + output={_config.Output.PYPROJECT}, + matrix={"cuda": ["100.17"]}, + prepend_channels=[], + to_stdout=True + ) + captured_stdout = capsys.readouterr().out + + # should be valid TOML, containing the expected dependencies and the other contents of + # the nested pyproject.toml file + doc = tomlkit.loads(captured_stdout) + assert doc["project"]["name"] == "beep-boop" + assert doc["project"]["version"] == "1.2.3" + assert sorted(doc["project"]["dependencies"]) == ["cuda-python>=100.1,<101.0a0", "fsspec>=0.6.0"] + + # and should NOT contain anything from the root-level pyproject.toml + assert set(dict(doc).keys()) == {"project"} + + def test_should_use_specific_entry(): # no match matrix_combo = {"cuda": "11.5", "arch": "x86_64"}