summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlec Scott <hi@alecbcs.com>2023-04-19 01:00:40 -0700
committerGitHub <noreply@github.com>2023-04-19 10:00:40 +0200
commit3a5e48f47686f2ed8ec296dccba81087010b2814 (patch)
treeec82eebe9843258886e95238150112e9205f855f
parent899838b32530bdf908a832c7946a8caa15297689 (diff)
downloadspack-3a5e48f47686f2ed8ec296dccba81087010b2814.tar.gz
spack-3a5e48f47686f2ed8ec296dccba81087010b2814.tar.bz2
spack-3a5e48f47686f2ed8ec296dccba81087010b2814.tar.xz
spack-3a5e48f47686f2ed8ec296dccba81087010b2814.zip
installer.py: drop build edges of installed packages by default (#36707)
This means that `spack install` will now build the minimal set of packages required to install the root(s). To opt out of build edge pruning, use `spack install --include-build-deps`. Co-authored-by: Harmen Stoppels <harmenstoppels@gmail.com>
-rw-r--r--lib/spack/spack/installer.py5
-rw-r--r--lib/spack/spack/test/installer.py48
2 files changed, 52 insertions, 1 deletions
diff --git a/lib/spack/spack/installer.py b/lib/spack/spack/installer.py
index 045e543e8c..4908fa7788 100644
--- a/lib/spack/spack/installer.py
+++ b/lib/spack/spack/installer.py
@@ -2420,7 +2420,10 @@ class BuildRequest(object):
else:
cache_only = self.install_args.get("dependencies_cache_only")
- if not cache_only or include_build_deps:
+ # Include build dependencies if pkg is not installed and cache_only
+ # is False, or if build depdencies are explicitly called for
+ # by include_build_deps.
+ if include_build_deps or not (cache_only or pkg.spec.installed):
deptypes.append("build")
if self.run_tests(pkg):
deptypes.append("test")
diff --git a/lib/spack/spack/test/installer.py b/lib/spack/spack/test/installer.py
index 76e987e1cd..4e92802b72 100644
--- a/lib/spack/spack/test/installer.py
+++ b/lib/spack/spack/test/installer.py
@@ -252,6 +252,54 @@ def test_installer_str(install_mockery):
assert "failed (0)" in istr
+def test_installer_prune_built_build_deps(install_mockery, monkeypatch, tmpdir):
+ r"""
+ Ensure that build dependencies of installed deps are pruned
+ from installer package queues.
+
+ (a)
+ / \
+ / \
+ (b) (c) <--- is installed already so we should
+ \ / | \ prune (f) from this install since
+ \ / | \ it is *only* needed to build (b)
+ (d) (e) (f)
+
+ Thus since (c) is already installed our build_pq dag should
+ only include four packages. [(a), (b), (c), (d), (e)]
+ """
+
+ @property
+ def _mock_installed(self):
+ return self.name in ["c"]
+
+ # Mock the installed property to say that (b) is installed
+ monkeypatch.setattr(spack.spec.Spec, "installed", _mock_installed)
+
+ # Create mock repository with packages (a), (b), (c), (d), and (e)
+ builder = spack.repo.MockRepositoryBuilder(tmpdir.mkdir("mock-repo"))
+
+ builder.add_package("a", dependencies=[("b", "build", None), ("c", "build", None)])
+ builder.add_package("b", dependencies=[("d", "build", None)])
+ builder.add_package(
+ "c", dependencies=[("d", "build", None), ("e", "all", None), ("f", "build", None)]
+ )
+ builder.add_package("d")
+ builder.add_package("e")
+ builder.add_package("f")
+
+ with spack.repo.use_repositories(builder.root):
+ const_arg = installer_args(["a"], {})
+ installer = create_installer(const_arg)
+
+ installer._init_queue()
+
+ # Assert that (c) is not in the build_pq
+ result = set([task.pkg_id[0] for _, task in installer.build_pq])
+ expected = set(["a", "b", "c", "d", "e"])
+ assert result == expected
+
+
def test_check_before_phase_error(install_mockery):
s = spack.spec.Spec("trivial-install-test-package").concretized()
s.package.stop_before_phase = "beforephase"