Skip to content

Commit

Permalink
Merge pull request #4754 from Flamefire/dict-improve
Browse files Browse the repository at this point in the history
Small improvements to `ModuleLoadEnvironment`
  • Loading branch information
boegel authored Feb 5, 2025
2 parents 1c69ff9 + a2c4c8c commit df528c6
Show file tree
Hide file tree
Showing 3 changed files with 20 additions and 25 deletions.
23 changes: 13 additions & 10 deletions easybuild/framework/easyblock.py
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,7 @@ class LibSymlink(Enum):
- LIB64_TO_LIB: 'lib64' is a symlink to 'lib'
- NEITHER: neither 'lib' is a symlink to 'lib64', nor 'lib64' is a symlink to 'lib'
- """
UNKNOWN, LIB_TO_LIB64, LIB64_TO_LIB, NEITHER = range(0, 4)
LIB_TO_LIB64, LIB64_TO_LIB, NEITHER = range(3)


class EasyBlock(object):
Expand Down Expand Up @@ -226,7 +226,7 @@ def __init__(self, ec, logfile=None):
self.install_subdir = None

# track status of symlink between library directories
self.install_lib_symlink = LibSymlink.UNKNOWN
self._install_lib_symlink = None

# indicates whether build should be performed in installation dir
self.build_in_installdir = self.cfg['buildininstalldir']
Expand Down Expand Up @@ -311,6 +311,13 @@ def __init__(self, ec, logfile=None):

self.log.info("Init completed for application name %s version %s" % (self.name, self.version))

@property
def install_lib_symlink(self):
"""Return symlink state of lib/lib64 folders"""
if self._install_lib_symlink is None:
self.check_install_lib_symlink()
return self._install_lib_symlink

def post_init(self):
"""
Run post-initialization tasks.
Expand Down Expand Up @@ -1719,10 +1726,6 @@ def expand_module_search_path(self, search_path, path_type=ModEnvVarType.PATH_WI
abs_glob = os.path.join(self.installdir, search_path)
exp_search_paths = [abs_glob] if search_path == "" else glob.glob(abs_glob)

# Explicitly check symlink state between lib dirs if it is still undefined (e.g. --module-only)
if self.install_lib_symlink == LibSymlink.UNKNOWN:
self.check_install_lib_symlink()

retained_search_paths = []
for abs_path in exp_search_paths:
# return relative paths
Expand Down Expand Up @@ -1751,16 +1754,16 @@ def expand_module_search_path(self, search_path, path_type=ModEnvVarType.PATH_WI
return retained_search_paths

def check_install_lib_symlink(self):
"""Check symlink state between library directories in installation prefix"""
"""Update the symlink state between library directories in installation prefix"""
lib_dir = os.path.join(self.installdir, 'lib')
lib64_dir = os.path.join(self.installdir, 'lib64')

self.install_lib_symlink = LibSymlink.NEITHER
self._install_lib_symlink = LibSymlink.NEITHER
if os.path.exists(lib_dir) and os.path.exists(lib64_dir):
if os.path.islink(lib_dir) and os.path.samefile(lib_dir, lib64_dir):
self.install_lib_symlink = LibSymlink.LIB_TO_LIB64
self._install_lib_symlink = LibSymlink.LIB_TO_LIB64
elif os.path.islink(lib64_dir) and os.path.samefile(lib_dir, lib64_dir):
self.install_lib_symlink = LibSymlink.LIB64_TO_LIB
self._install_lib_symlink = LibSymlink.LIB64_TO_LIB

def make_module_req_guess(self):
"""
Expand Down
17 changes: 5 additions & 12 deletions easybuild/tools/modules.py
Original file line number Diff line number Diff line change
Expand Up @@ -152,18 +152,15 @@ class ModuleEnvironmentVariable:
Contents of environment variable is a list of unique strings
"""

def __init__(self, contents, var_type=None, delim=os.pathsep):
def __init__(self, contents, var_type=ModEnvVarType.PATH_WITH_FILES, delim=os.pathsep):
"""
Initialize new environment variable
Actual contents of the environment variable are held in self.contents
By default, environment variable is a (list of) paths with files in them
By default, the environment variable is a list of paths with files in them
Existence of paths and their contents are not checked at init
"""
self.contents = contents
self.delim = delim

if var_type is None:
var_type = ModEnvVarType.PATH_WITH_FILES
self.type = var_type

self.log = fancylogger.getLogger(self.__class__.__name__, fname=False)
Expand Down Expand Up @@ -283,7 +280,7 @@ def __setattr__(self, name, value):

# special variables that require files in their top directories
if name in ('LD_LIBRARY_PATH', 'PATH'):
kwargs.update({'var_type': ModEnvVarType.PATH_WITH_TOP_FILES})
kwargs['var_type'] = ModEnvVarType.PATH_WITH_TOP_FILES

return super().__setattr__(name, ModuleEnvironmentVariable(contents, **kwargs))

Expand All @@ -297,8 +294,7 @@ def items(self):
- key = attribute name
- value = its "contents" attribute
"""
for attr in self.__dict__:
yield attr, getattr(self, attr)
return self.__dict__.items()

def update(self, new_env):
"""Update contents of environment from given dictionary"""
Expand All @@ -321,10 +317,7 @@ def environ(self):
Return dict with mapping of ModuleEnvironmentVariables names with their contents
Equivalent in shape to os.environ
"""
mapping = {}
for envar_name, envar_contents in self.items():
mapping.update({envar_name: str(envar_contents)})
return mapping
return {envar_name: str(envar_contents) for envar_name, envar_contents in self.items()}


class ModulesTool(object):
Expand Down
5 changes: 2 additions & 3 deletions test/framework/easyblock.py
Original file line number Diff line number Diff line change
Expand Up @@ -439,7 +439,7 @@ def test_make_module_req(self):
for path in ('bin', ('bin', 'testdir'), 'sbin', 'share', ('share', 'man'), 'lib', 'lib64'):
path_components = (path, ) if isinstance(path, str) else path
os.mkdir(os.path.join(eb.installdir, *path_components))
eb.install_lib_symlink = LibSymlink.NEITHER
eb.check_install_lib_symlink()

write_file(os.path.join(eb.installdir, 'foo.jar'), 'foo.jar')
write_file(os.path.join(eb.installdir, 'bla.jar'), 'bla.jar')
Expand Down Expand Up @@ -505,7 +505,7 @@ def test_make_module_req(self):
write_file(os.path.join(eb.installdir, 'lib', 'libfoo.so'), 'test')
shutil.rmtree(os.path.join(eb.installdir, 'lib64'))
os.symlink('lib', os.path.join(eb.installdir, 'lib64'))
eb.install_lib_symlink = LibSymlink.LIB64_TO_LIB
eb.check_install_lib_symlink()
with eb.module_generator.start_module_creation():
guess = eb.make_module_req()
if get_module_syntax() == 'Tcl':
Expand Down Expand Up @@ -3215,7 +3215,6 @@ def test_expand_module_search_path(self):
write_file(os.path.join(eb.installdir, 'dir_full_subdirs', 'subdir1', 'file12.txt'), 'test file 1.2')
write_file(os.path.join(eb.installdir, 'dir_full_subdirs', 'subdir2', 'file21.txt'), 'test file 2.1')

self.assertEqual(eb.install_lib_symlink, LibSymlink.UNKNOWN)
eb.check_install_lib_symlink()
self.assertEqual(eb.install_lib_symlink, LibSymlink.NEITHER)

Expand Down

0 comments on commit df528c6

Please sign in to comment.