Improve output of the external find command (#18017)
This commit adds output to the "spack external find" command to inform users of the result of the operation. It also fixes a bug introduced in #17804 due to the fact that a function was not updated to conform to the new packages.yaml format (_get_predefined_externals).
This commit is contained in:
parent
c0342e4152
commit
31f660bd90
@ -15,6 +15,7 @@
|
||||
import llnl.util.tty.colify as colify
|
||||
import six
|
||||
import spack
|
||||
import spack.cmd
|
||||
import spack.error
|
||||
import spack.util.environment
|
||||
import spack.util.spack_yaml as syaml
|
||||
@ -146,7 +147,17 @@ def external_find(args):
|
||||
packages_to_check = spack.repo.path.all_packages()
|
||||
|
||||
pkg_to_entries = _get_external_packages(packages_to_check)
|
||||
_update_pkg_config(pkg_to_entries, args.not_buildable)
|
||||
new_entries, write_scope = _update_pkg_config(
|
||||
pkg_to_entries, args.not_buildable
|
||||
)
|
||||
if new_entries:
|
||||
path = spack.config.config.get_config_filename(write_scope, 'packages')
|
||||
msg = ('The following specs have been detected on this system '
|
||||
'and added to {0}')
|
||||
tty.msg(msg.format(path))
|
||||
spack.cmd.display_specs(new_entries)
|
||||
else:
|
||||
tty.msg('No new external packages detected')
|
||||
|
||||
|
||||
def _group_by_prefix(paths):
|
||||
@ -188,23 +199,24 @@ def _get_predefined_externals():
|
||||
pkg_config = spack.config.get('packages')
|
||||
already_defined_specs = set()
|
||||
for pkg_name, per_pkg_cfg in pkg_config.items():
|
||||
paths = per_pkg_cfg.get('paths', {})
|
||||
already_defined_specs.update(spack.spec.Spec(k) for k in paths)
|
||||
modules = per_pkg_cfg.get('modules', {})
|
||||
already_defined_specs.update(spack.spec.Spec(k) for k in modules)
|
||||
for item in per_pkg_cfg.get('externals', []):
|
||||
already_defined_specs.add(spack.spec.Spec(item['spec']))
|
||||
return already_defined_specs
|
||||
|
||||
|
||||
def _update_pkg_config(pkg_to_entries, not_buildable):
|
||||
predefined_external_specs = _get_predefined_externals()
|
||||
|
||||
pkg_to_cfg = {}
|
||||
pkg_to_cfg, all_new_specs = {}, []
|
||||
for pkg_name, ext_pkg_entries in pkg_to_entries.items():
|
||||
new_entries = list(
|
||||
e for e in ext_pkg_entries
|
||||
if (e.spec not in predefined_external_specs))
|
||||
|
||||
pkg_config = _generate_pkg_config(new_entries)
|
||||
all_new_specs.extend([
|
||||
spack.spec.Spec(x['spec']) for x in pkg_config.get('externals', [])
|
||||
])
|
||||
if not_buildable:
|
||||
pkg_config['buildable'] = False
|
||||
pkg_to_cfg[pkg_name] = pkg_config
|
||||
@ -215,6 +227,8 @@ def _update_pkg_config(pkg_to_entries, not_buildable):
|
||||
spack.config.merge_yaml(pkgs_cfg, pkg_to_cfg)
|
||||
spack.config.set('packages', pkgs_cfg, scope=cfg_scope)
|
||||
|
||||
return all_new_specs, cfg_scope
|
||||
|
||||
|
||||
def _get_external_packages(packages_to_check, system_path_to_exe=None):
|
||||
if not system_path_to_exe:
|
||||
|
@ -222,3 +222,21 @@ def _determine_variants(cls, exes, version_str):
|
||||
externals = packages_yaml['gcc']['externals']
|
||||
assert len(externals) == 1
|
||||
assert externals[0]['prefix'] == '/opt/gcc/bin'
|
||||
|
||||
|
||||
def test_new_entries_are_reported_correctly(
|
||||
mock_executable, mutable_config, monkeypatch
|
||||
):
|
||||
# Prepare an environment to detect a fake gcc
|
||||
gcc_exe = mock_executable('gcc', output="echo 4.2.1")
|
||||
prefix = os.path.dirname(gcc_exe)
|
||||
monkeypatch.setenv('PATH', prefix)
|
||||
|
||||
# The first run will find and add the external gcc
|
||||
output = external('find', 'gcc')
|
||||
assert 'The following specs have been' in output
|
||||
|
||||
# The second run should report that no new external
|
||||
# has been found
|
||||
output = external('find', 'gcc')
|
||||
assert 'No new external packages detected' in output
|
||||
|
Loading…
Reference in New Issue
Block a user