Skip to content

Commit

Permalink
Merge pull request #349 from rfbgo/empty_env
Browse files Browse the repository at this point in the history
Allow for empty spack env
  • Loading branch information
douglasjacobsen authored Jan 19, 2024
2 parents cd61b83 + 636bba3 commit 424fd0f
Show file tree
Hide file tree
Showing 8 changed files with 55 additions and 22 deletions.
34 changes: 24 additions & 10 deletions lib/ramble/ramble/application.py
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,9 @@
from ramble.language.shared_language import SharedMeta, register_builtin
from ramble.error import RambleError

from enum import Enum
experiment_status = Enum('experiment_status', ['UNKNOWN', 'SETUP', 'SUCCESS', 'FAILED'])


class ApplicationBase(object, metaclass=ApplicationMeta):
name = None
Expand Down Expand Up @@ -1092,7 +1095,7 @@ def _make_experiments(self, workspace):

experiment_script = workspace.experiments_script
experiment_script.write(self.expander.expand_var('{batch_submit}\n'))
self.set_status(status='UNKNOWN')
self.set_status(status=experiment_status.SETUP)

def _clean_hash_variables(self, workspace, variables):
"""Cleanup variables to hash before computing the hash
Expand Down Expand Up @@ -1282,6 +1285,13 @@ def _analyze_experiments(self, workspace):
injected in a workspace config.
"""

if self.get_status() == experiment_status.UNKNOWN.name and not workspace.dry_run:
logger.die(
f'Workspace status is {self.get_status()}\n'
'Make sure your workspace is fully setup with\n'
' ramble workspace setup'
)

def format_context(context_match, context_format):

context_val = {}
Expand Down Expand Up @@ -1385,12 +1395,13 @@ def format_context(context_match, context_format):

logger.debug('fom_values = %s' % fom_values)
results['EXPERIMENT_CHAIN'] = self.chain_order.copy()

if success:
self.set_status(status='SUCCESS')
results['RAMBLE_STATUS'] = 'SUCCESS'
self.set_status(status=experiment_status.SUCCESS)
else:
self.set_status(status='FAILED')
results['RAMBLE_STATUS'] = 'FAILED'
self.set_status(status=experiment_status.FAILED)

results['RAMBLE_STATUS'] = self.get_status()

if success or workspace.always_print_foms:
results['RAMBLE_VARIABLES'] = {}
Expand Down Expand Up @@ -1542,7 +1553,7 @@ def read_status(self):
Set this experiment's status based on the status file in the experiment
run directory, if it exists. If it doesn't exist, set its status to
UNKNOWN
experiment_status.UNKNOWN
"""
status_path = os.path.join(
self.expander.expand_var_name(self.keywords.experiment_run_dir),
Expand All @@ -1555,12 +1566,15 @@ def read_status(self):
self.variables[self.keywords.experiment_status] = \
status_data[self.keywords.experiment_status]
else:
self.variables[self.keywords.experiment_status] = \
'UNKNOWN'
self.set_status(experiment_status.UNKNOWN)

def set_status(self, status='UNKNOWN'):
def set_status(self, status=experiment_status.UNKNOWN):
"""Set the status of this experiment"""
self.variables[self.keywords.experiment_status] = status
self.variables[self.keywords.experiment_status] = status.name

def get_status(self):
"""Get the status of this experiment"""
return self.variables[self.keywords.experiment_status]

register_phase('write_status', pipeline='analyze', depends_on=['analyze_experiments'])
register_phase('write_status', pipeline='setup', depends_on=['make_experiments'])
Expand Down
8 changes: 8 additions & 0 deletions lib/ramble/ramble/cmd/workspace.py
Original file line number Diff line number Diff line change
Expand Up @@ -405,6 +405,11 @@ def workspace_analyze_setup_parser(subparser):
help='Control if figures of merit are printed even if an experiment fails',
required=False)

subparser.add_argument(
'--dry-run', dest='dry_run',
action='store_true',
help='perform a dry run. Allows progress on workspaces which are not fully setup')

arguments.add_common_arguments(subparser, ['phases', 'include_phase_dependencies',
'where', 'exclude_where'])

Expand All @@ -414,6 +419,9 @@ def workspace_analyze(args):
ws = ramble.cmd.require_active_workspace(cmd_name='workspace analyze')
ws.always_print_foms = args.always_print_foms

if args.dry_run:
ws.dry_run = True

filters = ramble.filters.Filters(
phase_filters=args.phases,
include_where_filters=args.where,
Expand Down
9 changes: 9 additions & 0 deletions lib/ramble/ramble/pipeline.py
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,15 @@ def __init__(self, workspace, filters):
def _construct_hash(self):
"""Hash all of the experiments, construct workspace inventory"""
for exp, app_inst, _ in self._experiment_set.all_experiments():
if self.require_inventory:
if app_inst.get_status() == ramble.application.experiment_status.UNKNOWN.name:
if not self.workspace.dry_run:
logger.die(
f'Workspace status is {app_inst.get_status()}\n'
'Make sure your workspace is fully setup with\n'
' ramble workspace setup'
)

app_inst.populate_inventory(self.workspace,
force_compute=self.force_inventory,
require_exist=self.require_inventory)
Expand Down
17 changes: 9 additions & 8 deletions lib/ramble/ramble/spack_runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -602,14 +602,15 @@ def inventory_hash(self, require_exist=False):
contents_to_hash = None

if not self.dry_run:
if not lock_exists and (require_exist or len(self.env_contents) == 0):
logger.die(
'spack.lock file does not exist in environment '
f'{self.env_path}\n'
'Make sure your workspace is fully setup with\n'
' ramble workspace setup'
)
elif lock_exists:
if not lock_exists:
if require_exist and len(self.env_contents) > 0:
logger.die(
'spack.lock file does not exist in environment '
f'{self.env_path}\n'
'Make sure your workspace is fully setup with\n'
' ramble workspace setup'
)
else: # lock_exists
with open(spack_file, 'r') as f:
contents_to_hash = sjson.load(f)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,11 +54,12 @@ def test_exclusive_filtered_vector_workloads(mutable_config, mutable_mock_worksp

with open(config_path, 'w+') as f:
f.write(test_config)

ws._re_read()

workspace('setup', '--dry-run', '--exclude-where', '"{workload_name}" == "serial"',
global_args=['-w', workspace_name])
workspace('analyze', '--exclude-where', '"{workload_name}" == "serial"',
workspace('analyze', '--dry-run', '--exclude-where', '"{workload_name}" == "serial"',
global_args=['-w', workspace_name])
workspace('archive', '--exclude-where', '"{workload_name}" == "serial"',
global_args=['-w', workspace_name])
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ def test_inclusive_filtered_vector_workloads(mutable_config, mutable_mock_worksp

workspace('setup', '--dry-run', '--where', '"{workload_name}" == "serial"',
global_args=['-w', workspace_name])
workspace('analyze', '--where', '"{workload_name}" == "serial"',
workspace('analyze', '--dry-run', '--where', '"{workload_name}" == "serial"',
global_args=['-w', workspace_name])
workspace('archive', '--where', '"{workload_name}" == "serial"',
global_args=['-w', workspace_name])
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,4 +68,4 @@ def test_unsetup_workspace_cannot_analyze(mutable_config,
ws._re_read()
with pytest.raises(RambleCommandError):
output = workspace('analyze', global_args=['-w', workspace_name])
assert 'spack.lock file does not exist' in output
assert 'Make sure your workspace is fully setup' in output
2 changes: 1 addition & 1 deletion share/ramble/ramble-completion.bash
Original file line number Diff line number Diff line change
Expand Up @@ -670,7 +670,7 @@ _ramble_workspace_setup() {
}

_ramble_workspace_analyze() {
RAMBLE_COMPREPLY="-h --help -f --formats -u --upload --always-print-foms --phases --include-phase-dependencies --where --exclude-where"
RAMBLE_COMPREPLY="-h --help -f --formats -u --upload --always-print-foms --dry-run --phases --include-phase-dependencies --where --exclude-where"
}

_ramble_workspace_push_to_cache() {
Expand Down

0 comments on commit 424fd0f

Please sign in to comment.