env: spack install SPEC
installs into currently active environment.
- install will now add (if necessary), concretize, and install a single spec into the active environment.
This commit is contained in:
parent
3fd9fc8994
commit
9fb37dfd76
4 changed files with 100 additions and 9 deletions
|
@ -283,7 +283,7 @@ def env_list(args):
|
||||||
def env_add_setup_parser(subparser):
|
def env_add_setup_parser(subparser):
|
||||||
"""add a spec to an environment"""
|
"""add a spec to an environment"""
|
||||||
subparser.add_argument(
|
subparser.add_argument(
|
||||||
'-e', '--env', help='add spec to environment with this name')
|
'-e', '--env', help='add spec to this environment')
|
||||||
subparser.add_argument(
|
subparser.add_argument(
|
||||||
'specs', nargs=argparse.REMAINDER, help="spec of the package to add")
|
'specs', nargs=argparse.REMAINDER, help="spec of the package to add")
|
||||||
|
|
||||||
|
@ -371,7 +371,7 @@ def env_install(args):
|
||||||
env.write()
|
env.write()
|
||||||
|
|
||||||
# install all specs in the environment
|
# install all specs in the environment
|
||||||
env.install(args)
|
env.install_all(args)
|
||||||
|
|
||||||
|
|
||||||
# REMOVE
|
# REMOVE
|
||||||
|
|
|
@ -150,17 +150,27 @@ def default_log_file(spec):
|
||||||
|
|
||||||
|
|
||||||
def install_spec(cli_args, kwargs, spec):
|
def install_spec(cli_args, kwargs, spec):
|
||||||
# Do the actual installation
|
"""Do the actual installation."""
|
||||||
|
|
||||||
|
# handle active environment, if any
|
||||||
|
def install(spec, kwargs):
|
||||||
|
env = spack.environment.active
|
||||||
|
if env:
|
||||||
|
new_specs = env.install(spec, kwargs)
|
||||||
|
env.write(dump_packages=new_specs)
|
||||||
|
else:
|
||||||
|
spec.package.do_install(**kwargs)
|
||||||
|
|
||||||
try:
|
try:
|
||||||
if cli_args.things_to_install == 'dependencies':
|
if cli_args.things_to_install == 'dependencies':
|
||||||
# Install dependencies as-if they were installed
|
# Install dependencies as-if they were installed
|
||||||
# for root (explicit=False in the DB)
|
# for root (explicit=False in the DB)
|
||||||
kwargs['explicit'] = False
|
kwargs['explicit'] = False
|
||||||
for s in spec.dependencies():
|
for s in spec.dependencies():
|
||||||
s.package.do_install(**kwargs)
|
install(s, kwargs)
|
||||||
else:
|
else:
|
||||||
kwargs['explicit'] = True
|
kwargs['explicit'] = True
|
||||||
spec.package.do_install(**kwargs)
|
install(spec, kwargs)
|
||||||
|
|
||||||
except spack.build_environment.InstallError as e:
|
except spack.build_environment.InstallError as e:
|
||||||
if cli_args.show_log_on_error:
|
if cli_args.show_log_on_error:
|
||||||
|
|
|
@ -116,9 +116,29 @@ def deactivate():
|
||||||
|
|
||||||
"""
|
"""
|
||||||
global active
|
global active
|
||||||
|
|
||||||
if not active:
|
if not active:
|
||||||
return
|
return
|
||||||
|
|
||||||
|
deactivate_config_scope(active)
|
||||||
|
spack.repo.path.remove(active.repo)
|
||||||
|
|
||||||
|
tty.debug("Deactivated environmennt '%s'" % active.name)
|
||||||
|
active = None
|
||||||
|
|
||||||
|
|
||||||
|
@contextmanager
|
||||||
|
def env_context(env):
|
||||||
|
"""Context manager that activates and deactivates an environment."""
|
||||||
|
old_active = active
|
||||||
|
activate(env)
|
||||||
|
|
||||||
|
yield
|
||||||
|
|
||||||
|
deactivate()
|
||||||
|
if old_active:
|
||||||
|
activate(old_active)
|
||||||
|
|
||||||
|
|
||||||
def root(name):
|
def root(name):
|
||||||
"""Get the root directory for an environment by name."""
|
"""Get the root directory for an environment by name."""
|
||||||
|
@ -333,7 +353,7 @@ def destroy(self):
|
||||||
"""Remove this environment from Spack entirely."""
|
"""Remove this environment from Spack entirely."""
|
||||||
shutil.rmtree(self.path)
|
shutil.rmtree(self.path)
|
||||||
|
|
||||||
def add(self, user_spec, report_existing=True):
|
def add(self, user_spec):
|
||||||
"""Add a single user_spec (non-concretized) to the Environment
|
"""Add a single user_spec (non-concretized) to the Environment
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
|
@ -342,6 +362,10 @@ def add(self, user_spec, report_existing=True):
|
||||||
|
|
||||||
"""
|
"""
|
||||||
spec = Spec(user_spec)
|
spec = Spec(user_spec)
|
||||||
|
if not spec.name:
|
||||||
|
raise EnvError('cannot add anonymous specs to an environment!')
|
||||||
|
elif not spack.repo.path.exists(spec.name):
|
||||||
|
raise EnvError('no such package: %s' % spec.name)
|
||||||
|
|
||||||
existing = set(s for s in self.user_specs if s.name == spec.name)
|
existing = set(s for s in self.user_specs if s.name == spec.name)
|
||||||
if not existing:
|
if not existing:
|
||||||
|
@ -425,7 +449,45 @@ def concretize(self, force=False):
|
||||||
# return only the newly concretized specs
|
# return only the newly concretized specs
|
||||||
return new_specs
|
return new_specs
|
||||||
|
|
||||||
def install(self, args=None):
|
def install(self, user_spec, install_args=None):
|
||||||
|
"""Install a single spec into an environment.
|
||||||
|
|
||||||
|
This will automatically concretize the single spec, but it won't
|
||||||
|
affect other as-yet unconcretized specs.
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
(Spec): concrete spec if the spec was installed, None if it
|
||||||
|
was already present and installed.
|
||||||
|
|
||||||
|
"""
|
||||||
|
spec = Spec(user_spec)
|
||||||
|
|
||||||
|
# TODO: do a more sophisticated match than just by name
|
||||||
|
added = self.add(spec)
|
||||||
|
concrete = None
|
||||||
|
if added:
|
||||||
|
# newly added spec
|
||||||
|
spec = self.user_specs[-1]
|
||||||
|
concrete = spec.concretized()
|
||||||
|
h = concrete.dag_hash()
|
||||||
|
|
||||||
|
self.concretized_user_specs.append(spec)
|
||||||
|
self.concretized_order.append(h)
|
||||||
|
self.specs_by_hash[h] = concrete
|
||||||
|
|
||||||
|
else:
|
||||||
|
# spec might be in the user_specs, but not installed.
|
||||||
|
spec = next(s for s in self.user_specs if s.name == spec.name)
|
||||||
|
if spec not in self.concretized_user_specs:
|
||||||
|
concrete = spec.concretized()
|
||||||
|
self.concretized_user_specs.append(spec)
|
||||||
|
self.concretized_order.append(h)
|
||||||
|
self.specs_by_hash[h] = concrete
|
||||||
|
|
||||||
|
if concrete:
|
||||||
|
spec.package.do_install(**install_args)
|
||||||
|
|
||||||
|
def install_all(self, args=None):
|
||||||
"""Install all concretized specs in an environment."""
|
"""Install all concretized specs in an environment."""
|
||||||
|
|
||||||
# Make sure log directory exists
|
# Make sure log directory exists
|
||||||
|
@ -706,6 +768,12 @@ def prepare_config_scope(env):
|
||||||
spack.config.config.push_scope(scope)
|
spack.config.config.push_scope(scope)
|
||||||
|
|
||||||
|
|
||||||
|
def deactivate_config_scope(env):
|
||||||
|
"""Remove any scopes from env from the global config path."""
|
||||||
|
for scope in env.config_scopes():
|
||||||
|
spack.config.config.remove_scope(scope.name)
|
||||||
|
|
||||||
|
|
||||||
class EnvError(spack.error.SpackError):
|
class EnvError(spack.error.SpackError):
|
||||||
"""Superclass for all errors to do with Spack environments.
|
"""Superclass for all errors to do with Spack environments.
|
||||||
|
|
||||||
|
|
|
@ -71,16 +71,29 @@ def test_concretize():
|
||||||
assert any(x.name == 'mpileaks' for x in env_specs)
|
assert any(x.name == 'mpileaks' for x in env_specs)
|
||||||
|
|
||||||
|
|
||||||
def test_env_install(install_mockery, mock_fetch):
|
def test_env_install_all(install_mockery, mock_fetch):
|
||||||
e = ev.Environment('test')
|
e = ev.Environment('test')
|
||||||
e.add('cmake-client')
|
e.add('cmake-client')
|
||||||
e.concretize()
|
e.concretize()
|
||||||
e.install()
|
e.install_all()
|
||||||
env_specs = e._get_environment_specs()
|
env_specs = e._get_environment_specs()
|
||||||
spec = next(x for x in env_specs if x.name == 'cmake-client')
|
spec = next(x for x in env_specs if x.name == 'cmake-client')
|
||||||
assert spec.package.installed
|
assert spec.package.installed
|
||||||
|
|
||||||
|
|
||||||
|
def test_env_install(install_mockery, mock_fetch):
|
||||||
|
env('create', 'test')
|
||||||
|
install = SpackCommand('install')
|
||||||
|
|
||||||
|
with ev.env_context('test'):
|
||||||
|
install('cmake-client')
|
||||||
|
|
||||||
|
e = ev.read('test')
|
||||||
|
assert e.user_specs[0].name == 'cmake-client'
|
||||||
|
assert e.concretized_user_specs[0].name == 'cmake-client'
|
||||||
|
assert e.specs_by_hash[e.concretized_order[0]].name == 'cmake-client'
|
||||||
|
|
||||||
|
|
||||||
def test_remove_after_concretize():
|
def test_remove_after_concretize():
|
||||||
e = ev.Environment('test')
|
e = ev.Environment('test')
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue