From 0d31f6e88698317a0361183d19939159c65ef5ac Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 1 Apr 2026 16:44:16 +0200 Subject: [PATCH 01/12] Update JuliaPackage easyblock to avoid writing to $HOME & cleanup JuliaBundle --- easybuild/easyblocks/generic/juliabundle.py | 18 +--------- easybuild/easyblocks/generic/juliapackage.py | 36 ++++++++++++++++++-- 2 files changed, 35 insertions(+), 19 deletions(-) diff --git a/easybuild/easyblocks/generic/juliabundle.py b/easybuild/easyblocks/generic/juliabundle.py index d4fa09f8b5c..1d97897b0ef 100644 --- a/easybuild/easyblocks/generic/juliabundle.py +++ b/easybuild/easyblocks/generic/juliabundle.py @@ -76,23 +76,7 @@ def __init__(self, *args, **kwargs): self.log.info("exts_default_options: %s", self.cfg['exts_default_options']) - def prepare_step(self, *args, **kwargs): - """Prepare for installing bundle of Julia packages.""" - super().prepare_step(*args, **kwargs) - def install_step(self): - """Prepare installation environment and dd all dependencies to project environment.""" + """Prepare installation environment and add all dependencies to project environment.""" self.prepare_julia_env() self.include_pkg_dependencies() - - def sanity_check_step(self, *args, **kwargs): - """Custom sanity check for bundle of Julia packages""" - custom_paths = { - 'files': [], - 'dirs': [os.path.join('packages', self.name)], - } - super().sanity_check_step(custom_paths=custom_paths) - - def make_module_extra(self, *args, **kwargs): - """Custom module environment from JuliaPackage""" - return super().make_module_extra(*args, **kwargs) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index a3e641b2178..a3263f29a7b 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -31,6 +31,7 @@ import glob import os import re +import tempfile from easybuild.tools import LooseVersion @@ -118,6 +119,11 @@ def get_julia_env(env_var): return parsed_var + def __init__(self, *args, **kwargs): + """Initialize JuliaPackage easyblock.""" + super().__init__(*args, **kwargs) + self.tmp_depot_path = tempfile.mkdtemp(suffix='-julia_depot') + def julia_env_path(self, absolute=True, base=True): """ Return path to installation environment file. @@ -294,6 +300,32 @@ def install_extension(self): self.prepare_julia_env() self.install_pkg() + def fixup_sanity_check_commands(self): + """Set $JULIA_DEPOT_PATH for sanity check commands that run julia""" + with self.cfg.disable_templating(): + # If the sanity check commands run a julia command we + JULIA_CMD = 'julia -e' + def need_fixup(cmd): + return JULIA_CMD in cmd and 'JULIA_DEPOT_PATH' not in cmd + cmds = self.cfg['sanity_check_commands'] + if any(need_fixup(cmd) for cmd in cmds): + tmp_julia_depot = tempfile.mkdtemp(suffix='-julia_depot') + export = f'export JULIA_DEPOT_PATH="{tmp_julia_depot}$JULIA_DEPOT_PATH:"' + cmds = [f'{export} && {cmd}' if need_fixup(cmd) else cmd for cmd in cmds] + self.cfg['sanity_check_commands'] = cmds + self.log.info("Updated sanity check commands with temporary JULIA_DEPOT_PATH: %s", tmp_julia_depot) + + def load_module(self, *args, **kwargs): + """Set JULIA_DEPOT_PATH to a temporary directory and exclude the users depot path to avoid writing to $HOME + + Required for e.g. sanity checks that run a julia command. + """ + super().load_module(*args, **kwargs) + + depot_path = os.environ['JULIA_DEPOT_PATH'].strip(':') # Always set by module + # Append a colon at the end to exclude the users depot path (in $HOME) + env.setvar('JULIA_DEPOT_PATH', f"{self.tmp_depot_path}:{depot_path}:") + def sanity_check_step(self, *args, **kwargs): """Custom sanity check for JuliaPackage""" @@ -303,9 +335,9 @@ def sanity_check_step(self, *args, **kwargs): 'files': [], 'dirs': [pkg_dir], } - kwargs.update({'custom_paths': custom_paths}) + kwargs.setdefault('custom_paths', custom_paths) - return ExtensionEasyBlock.sanity_check_step(self, EXTS_FILTER_JULIA_PACKAGES, *args, **kwargs) + return super().sanity_check_step(EXTS_FILTER_JULIA_PACKAGES, *args, **kwargs) def make_module_extra(self, *args, **kwargs): """ From bf4e97f82b22a1c48d1739eb226c090c3375414c Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 1 Apr 2026 16:46:32 +0200 Subject: [PATCH 02/12] Remove old method --- easybuild/easyblocks/generic/juliabundle.py | 2 -- easybuild/easyblocks/generic/juliapackage.py | 15 --------------- 2 files changed, 17 deletions(-) diff --git a/easybuild/easyblocks/generic/juliabundle.py b/easybuild/easyblocks/generic/juliabundle.py index 1d97897b0ef..26945de6f7d 100644 --- a/easybuild/easyblocks/generic/juliabundle.py +++ b/easybuild/easyblocks/generic/juliabundle.py @@ -27,8 +27,6 @@ @author: Alex Domingo (Vrije Universiteit Brussel) """ -import os - from easybuild.easyblocks.generic.bundle import Bundle from easybuild.easyblocks.generic.juliapackage import EXTS_FILTER_JULIA_PACKAGES, JuliaPackage diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index a3263f29a7b..e5b72289ce2 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -300,21 +300,6 @@ def install_extension(self): self.prepare_julia_env() self.install_pkg() - def fixup_sanity_check_commands(self): - """Set $JULIA_DEPOT_PATH for sanity check commands that run julia""" - with self.cfg.disable_templating(): - # If the sanity check commands run a julia command we - JULIA_CMD = 'julia -e' - def need_fixup(cmd): - return JULIA_CMD in cmd and 'JULIA_DEPOT_PATH' not in cmd - cmds = self.cfg['sanity_check_commands'] - if any(need_fixup(cmd) for cmd in cmds): - tmp_julia_depot = tempfile.mkdtemp(suffix='-julia_depot') - export = f'export JULIA_DEPOT_PATH="{tmp_julia_depot}$JULIA_DEPOT_PATH:"' - cmds = [f'{export} && {cmd}' if need_fixup(cmd) else cmd for cmd in cmds] - self.cfg['sanity_check_commands'] = cmds - self.log.info("Updated sanity check commands with temporary JULIA_DEPOT_PATH: %s", tmp_julia_depot) - def load_module(self, *args, **kwargs): """Set JULIA_DEPOT_PATH to a temporary directory and exclude the users depot path to avoid writing to $HOME From 9cddef3771e627267dbc3760c6e1b6cef307ca1d Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 1 Apr 2026 16:53:50 +0200 Subject: [PATCH 03/12] Make tmpdir creation lazy --- easybuild/easyblocks/generic/juliapackage.py | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index e5b72289ce2..6269ba2e6f7 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -122,7 +122,14 @@ def get_julia_env(env_var): def __init__(self, *args, **kwargs): """Initialize JuliaPackage easyblock.""" super().__init__(*args, **kwargs) - self.tmp_depot_path = tempfile.mkdtemp(suffix='-julia_depot') + self._tmp_depot_path = None + + @property + def tmp_depot_path(self): + """Temporary path to be used as top DEPOT_PATH during module load.""" + if not self._tmp_depot_path: + self._tmp_depot_path = tempfile.mkdtemp(suffix='-julia_depot') + return self._tmp_depot_path def julia_env_path(self, absolute=True, base=True): """ From ed67a9ed133574e07afa7e20314a84ca2cd3297d Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 1 Apr 2026 17:50:03 +0200 Subject: [PATCH 04/12] Remove variable --- easybuild/easyblocks/generic/juliapackage.py | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index 6269ba2e6f7..7023e9fc669 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -272,6 +272,7 @@ def install_pkg(self): def prepare_step(self, *args, **kwargs): """Prepare for Julia package installation.""" super().prepare_step(*args, **kwargs) + print("Julia prepare") if get_software_root('Julia') is None: raise EasyBuildError("Julia not included as dependency!") @@ -321,11 +322,9 @@ def load_module(self, *args, **kwargs): def sanity_check_step(self, *args, **kwargs): """Custom sanity check for JuliaPackage""" - pkg_dir = os.path.join('packages', self.name) - custom_paths = { 'files': [], - 'dirs': [pkg_dir], + 'dirs': [os.path.join('packages', self.name)], } kwargs.setdefault('custom_paths', custom_paths) From 19e9487ba4e4e2b23c138038f9798cba0a8b34da Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Tue, 28 Apr 2026 18:08:39 +0200 Subject: [PATCH 05/12] Remove debug print --- easybuild/easyblocks/generic/juliapackage.py | 1 - 1 file changed, 1 deletion(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index 7023e9fc669..fe5f2335d81 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -272,7 +272,6 @@ def install_pkg(self): def prepare_step(self, *args, **kwargs): """Prepare for Julia package installation.""" super().prepare_step(*args, **kwargs) - print("Julia prepare") if get_software_root('Julia') is None: raise EasyBuildError("Julia not included as dependency!") From 8b12a839b319a0aec2a39ff6367165de05bf0a13 Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 29 Apr 2026 11:16:26 +0200 Subject: [PATCH 06/12] Use `prepare_julia_env` instead of setting `JULIA_DEPOT_PATH` in `load_module` & cache results --- easybuild/easyblocks/generic/juliapackage.py | 66 ++++++++++---------- 1 file changed, 32 insertions(+), 34 deletions(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index fe5f2335d81..12c75f64cc0 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -31,7 +31,6 @@ import glob import os import re -import tempfile from easybuild.tools import LooseVersion @@ -122,14 +121,10 @@ def get_julia_env(env_var): def __init__(self, *args, **kwargs): """Initialize JuliaPackage easyblock.""" super().__init__(*args, **kwargs) - self._tmp_depot_path = None - - @property - def tmp_depot_path(self): - """Temporary path to be used as top DEPOT_PATH during module load.""" - if not self._tmp_depot_path: - self._tmp_depot_path = tempfile.mkdtemp(suffix='-julia_depot') - return self._tmp_depot_path + # JULIA_DEPOT_PATH and JULIA_LOAD_PATH after cleaning them from e.g. $HOME paths + # Set by `prepare_julia_env` and cached here + self.clean_depot_path = None + self.clean_load_path = None def julia_env_path(self, absolute=True, base=True): """ @@ -179,24 +174,31 @@ def prepare_julia_env(self): 4. Enable automatic precompilation of packages after each build. """ - # Grab both DEPOT_PATH and LOAD_PATH before any changes are made - # given that Julia might automatically update LOAD_PATH from a change on DEPOT_PATH - dirty_depot = self.get_julia_env("DEPOT_PATH") - self.log.debug('DEPOT_PATH read from Julia environment: %s', os.pathsep.join(dirty_depot)) - dirty_load = self.get_julia_env("LOAD_PATH") - self.log.debug('LOAD_PATH read from Julia environment: %s', os.pathsep.join(dirty_load)) - - # First set DEPOT_PATH and then LOAD_PATH to avoid any automatic changes made by Julia - clean_depot = [path for path in dirty_depot if not USER_DEPOT_PATTERN.search(path) and path != self.installdir] - install_depot = os.pathsep.join([self.installdir] + clean_depot) - self.log.debug("Preparing Julia 'DEPOT_PATH' for installation: %s", install_depot) - env.setvar("JULIA_DEPOT_PATH", install_depot) - - project_toml = self.julia_env_path(base=False) - clean_load = [path for path in dirty_load if not USER_DEPOT_PATTERN.search(path) and path != project_toml] - install_load = os.pathsep.join([project_toml] + clean_load) - self.log.debug("Preparing Julia 'LOAD_PATH' for installation: %s", install_load) - env.setvar("JULIA_LOAD_PATH", install_load) + if self.clean_depot_path and self.clean_load_path: + env.setvar("JULIA_DEPOT_PATH", self.clean_depot_path) + env.setvar("JULIA_LOAD_PATH", self.clean_load_path) + else: + # Grab both DEPOT_PATH and LOAD_PATH before any changes are made + # given that Julia might automatically update LOAD_PATH from a change on DEPOT_PATH + dirty_depot = self.get_julia_env("DEPOT_PATH") + self.log.debug('DEPOT_PATH read from Julia environment: %s', os.pathsep.join(dirty_depot)) + dirty_load = self.get_julia_env("LOAD_PATH") + self.log.debug('LOAD_PATH read from Julia environment: %s', os.pathsep.join(dirty_load)) + + # First set DEPOT_PATH and then LOAD_PATH to avoid any automatic changes made by Julia + clean_depot = [path for path in dirty_depot + if not USER_DEPOT_PATTERN.search(path) and path != self.installdir] + install_depot = os.pathsep.join([self.installdir] + clean_depot) + self.log.debug("Preparing Julia 'DEPOT_PATH' for installation: %s", install_depot) + env.setvar("JULIA_DEPOT_PATH", install_depot) + self.clean_depot_path = install_depot + + project_toml = self.julia_env_path(base=False) + clean_load = [path for path in dirty_load if not USER_DEPOT_PATTERN.search(path) and path != project_toml] + install_load = os.pathsep.join([project_toml] + clean_load) + self.log.debug("Preparing Julia 'LOAD_PATH' for installation: %s", install_load) + env.setvar("JULIA_LOAD_PATH", install_load) + self.clean_load_path = install_load if self.julia_env_path(base=False) not in self.get_julia_env("LOAD_PATH"): errmsg = "Failed to prepare Julia environment for installation of: %s" @@ -298,7 +300,6 @@ def install_step(self): def install_extension(self): """Install Julia package as an extension.""" - if not self.src: errmsg = "No source found for Julia package %s, required for installation. (src: %s)" raise EasyBuildError(errmsg, self.name, self.src) @@ -308,15 +309,12 @@ def install_extension(self): self.install_pkg() def load_module(self, *args, **kwargs): - """Set JULIA_DEPOT_PATH to a temporary directory and exclude the users depot path to avoid writing to $HOME + """Set JULIA_DEPOT_PATH excluding the users depot path to avoid writing to $HOME Required for e.g. sanity checks that run a julia command. """ super().load_module(*args, **kwargs) - - depot_path = os.environ['JULIA_DEPOT_PATH'].strip(':') # Always set by module - # Append a colon at the end to exclude the users depot path (in $HOME) - env.setvar('JULIA_DEPOT_PATH', f"{self.tmp_depot_path}:{depot_path}:") + self.prepare_julia_env() def sanity_check_step(self, *args, **kwargs): """Custom sanity check for JuliaPackage""" @@ -339,7 +337,7 @@ def make_module_extra(self, *args, **kwargs): allowing user to add custom Julia packages while having packages in this installation available. See issue easybuilders/easybuild-easyconfigs#17455 """ - mod = super().make_module_extra() + mod = super().make_module_extra(*args, **kwargs) if self.module_generator.SYNTAX: mod += JULIA_PATHS_SOFT_INIT[self.module_generator.SYNTAX] mod += self.module_generator.append_paths('JULIA_DEPOT_PATH', ['']) From acae9a590104e5ea7b0421ed6215205ac2815748 Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 29 Apr 2026 13:00:06 +0200 Subject: [PATCH 07/12] Use temporary folder as first folderin `load_module` --- easybuild/easyblocks/generic/juliapackage.py | 75 ++++++++++++-------- 1 file changed, 45 insertions(+), 30 deletions(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index 12c75f64cc0..cd849cde80e 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -31,6 +31,7 @@ import glob import os import re +import tempfile from easybuild.tools import LooseVersion @@ -121,10 +122,14 @@ def get_julia_env(env_var): def __init__(self, *args, **kwargs): """Initialize JuliaPackage easyblock.""" super().__init__(*args, **kwargs) - # JULIA_DEPOT_PATH and JULIA_LOAD_PATH after cleaning them from e.g. $HOME paths - # Set by `prepare_julia_env` and cached here - self.clean_depot_path = None - self.clean_load_path = None + self._tmp_depot_path = None + + @property + def tmp_depot_path(self): + """Temporary path to be used as top DEPOT_PATH during module load.""" + if not self._tmp_depot_path: + self._tmp_depot_path = tempfile.mkdtemp(suffix='-julia_depot') + return self._tmp_depot_path def julia_env_path(self, absolute=True, base=True): """ @@ -158,6 +163,23 @@ def set_pkg_offline(self): ) raise EasyBuildError(errmsg, julia_version) + def determine_clean_paths(self): + """Determine cleaned DEPOT_PATH and LOAD_PATH excluding user depot paths.""" + # Grab both DEPOT_PATH and LOAD_PATH before any changes are made + # given that Julia might automatically update LOAD_PATH from a change on DEPOT_PATH + dirty_depot = self.get_julia_env("DEPOT_PATH") + self.log.debug('DEPOT_PATH read from Julia environment: %s', os.pathsep.join(dirty_depot)) + dirty_load = self.get_julia_env("LOAD_PATH") + self.log.debug('LOAD_PATH read from Julia environment: %s', os.pathsep.join(dirty_load)) + + clean_depot = [path for path in dirty_depot + if not USER_DEPOT_PATTERN.search(path) and path != self.installdir] + + project_toml = self.julia_env_path(base=False) + clean_load = [path for path in dirty_load if not USER_DEPOT_PATTERN.search(path) and path != project_toml] + + return clean_depot, clean_load + def prepare_julia_env(self): """ 1. Remove user depot and prepend installation directory to DEPOT_PATH. @@ -174,31 +196,14 @@ def prepare_julia_env(self): 4. Enable automatic precompilation of packages after each build. """ - if self.clean_depot_path and self.clean_load_path: - env.setvar("JULIA_DEPOT_PATH", self.clean_depot_path) - env.setvar("JULIA_LOAD_PATH", self.clean_load_path) - else: - # Grab both DEPOT_PATH and LOAD_PATH before any changes are made - # given that Julia might automatically update LOAD_PATH from a change on DEPOT_PATH - dirty_depot = self.get_julia_env("DEPOT_PATH") - self.log.debug('DEPOT_PATH read from Julia environment: %s', os.pathsep.join(dirty_depot)) - dirty_load = self.get_julia_env("LOAD_PATH") - self.log.debug('LOAD_PATH read from Julia environment: %s', os.pathsep.join(dirty_load)) - - # First set DEPOT_PATH and then LOAD_PATH to avoid any automatic changes made by Julia - clean_depot = [path for path in dirty_depot - if not USER_DEPOT_PATTERN.search(path) and path != self.installdir] - install_depot = os.pathsep.join([self.installdir] + clean_depot) - self.log.debug("Preparing Julia 'DEPOT_PATH' for installation: %s", install_depot) - env.setvar("JULIA_DEPOT_PATH", install_depot) - self.clean_depot_path = install_depot - - project_toml = self.julia_env_path(base=False) - clean_load = [path for path in dirty_load if not USER_DEPOT_PATTERN.search(path) and path != project_toml] - install_load = os.pathsep.join([project_toml] + clean_load) - self.log.debug("Preparing Julia 'LOAD_PATH' for installation: %s", install_load) - env.setvar("JULIA_LOAD_PATH", install_load) - self.clean_load_path = install_load + clean_depot, clean_load = self.determine_clean_paths() + install_depot = os.pathsep.join([self.installdir] + clean_depot) + self.log.debug("Preparing Julia 'DEPOT_PATH' for installation: %s", install_depot) + env.setvar("JULIA_DEPOT_PATH", install_depot) + project_toml = self.julia_env_path(base=False) + install_load = os.pathsep.join([project_toml] + clean_load) + self.log.debug("Preparing Julia 'LOAD_PATH' for installation: %s", install_load) + env.setvar("JULIA_LOAD_PATH", install_load) if self.julia_env_path(base=False) not in self.get_julia_env("LOAD_PATH"): errmsg = "Failed to prepare Julia environment for installation of: %s" @@ -314,7 +319,17 @@ def load_module(self, *args, **kwargs): Required for e.g. sanity checks that run a julia command. """ super().load_module(*args, **kwargs) - self.prepare_julia_env() + + if LooseVersion(get_software_version('Julia')) >= LooseVersion('1.11'): + depot_path = os.environ['JULIA_DEPOT_PATH'].strip(':') # Always set by module + # Append a colon at the end to exclude the users depot path (in $HOME) + depot_path += ':' + else: + # In older Julia versions the trailing colon doesn't prevent the user $HOME being added + # So use the extra logic to avoid that, see https://github.com/easybuilders/easybuild-easyblocks/pull/4102 + depot_path, _ = self.determine_clean_paths() + # Prepend a temporary directory so the install path is not affected by sanity checks + env.setvar('JULIA_DEPOT_PATH', f"{self.tmp_depot_path}:{depot_path}") def sanity_check_step(self, *args, **kwargs): """Custom sanity check for JuliaPackage""" From b56cb13d1c01eca073dd23386444b594cecd0eb0 Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 29 Apr 2026 13:00:45 +0200 Subject: [PATCH 08/12] Disable downloads in `load_module` --- easybuild/easyblocks/generic/juliapackage.py | 1 + 1 file changed, 1 insertion(+) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index cd849cde80e..4e39609019f 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -330,6 +330,7 @@ def load_module(self, *args, **kwargs): depot_path, _ = self.determine_clean_paths() # Prepend a temporary directory so the install path is not affected by sanity checks env.setvar('JULIA_DEPOT_PATH', f"{self.tmp_depot_path}:{depot_path}") + self.set_pkg_offline() def sanity_check_step(self, *args, **kwargs): """Custom sanity check for JuliaPackage""" From 7cf6413112cbce924fcdeb458ae01ce1e13cf618 Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Wed, 29 Apr 2026 17:19:11 +0200 Subject: [PATCH 09/12] Fix use of list of paths --- easybuild/easyblocks/generic/juliapackage.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index 4e39609019f..8a9cefb89ee 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -32,6 +32,7 @@ import os import re import tempfile +from typing import List, Tuple from easybuild.tools import LooseVersion @@ -163,7 +164,7 @@ def set_pkg_offline(self): ) raise EasyBuildError(errmsg, julia_version) - def determine_clean_paths(self): + def determine_clean_paths(self) -> Tuple[List[str], List[str]]: """Determine cleaned DEPOT_PATH and LOAD_PATH excluding user depot paths.""" # Grab both DEPOT_PATH and LOAD_PATH before any changes are made # given that Julia might automatically update LOAD_PATH from a change on DEPOT_PATH @@ -327,7 +328,7 @@ def load_module(self, *args, **kwargs): else: # In older Julia versions the trailing colon doesn't prevent the user $HOME being added # So use the extra logic to avoid that, see https://github.com/easybuilders/easybuild-easyblocks/pull/4102 - depot_path, _ = self.determine_clean_paths() + depot_path = os.pathsep.join(self.determine_clean_paths()[0]) # Prepend a temporary directory so the install path is not affected by sanity checks env.setvar('JULIA_DEPOT_PATH', f"{self.tmp_depot_path}:{depot_path}") self.set_pkg_offline() @@ -340,7 +341,6 @@ def sanity_check_step(self, *args, **kwargs): 'dirs': [os.path.join('packages', self.name)], } kwargs.setdefault('custom_paths', custom_paths) - return super().sanity_check_step(EXTS_FILTER_JULIA_PACKAGES, *args, **kwargs) def make_module_extra(self, *args, **kwargs): From ec598af27960232572f5707328909c7915ab9285 Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Thu, 30 Apr 2026 18:35:10 +0200 Subject: [PATCH 10/12] Keep installdir when cleaning DEPOT_PATH --- easybuild/easyblocks/generic/juliapackage.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index 8a9cefb89ee..bdad474cb9c 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -164,7 +164,7 @@ def set_pkg_offline(self): ) raise EasyBuildError(errmsg, julia_version) - def determine_clean_paths(self) -> Tuple[List[str], List[str]]: + def determine_clean_paths(self, keep_installdir=False) -> Tuple[List[str], List[str]]: """Determine cleaned DEPOT_PATH and LOAD_PATH excluding user depot paths.""" # Grab both DEPOT_PATH and LOAD_PATH before any changes are made # given that Julia might automatically update LOAD_PATH from a change on DEPOT_PATH @@ -174,7 +174,7 @@ def determine_clean_paths(self) -> Tuple[List[str], List[str]]: self.log.debug('LOAD_PATH read from Julia environment: %s', os.pathsep.join(dirty_load)) clean_depot = [path for path in dirty_depot - if not USER_DEPOT_PATTERN.search(path) and path != self.installdir] + if not USER_DEPOT_PATTERN.search(path) and (keep_installdir or path != self.installdir)] project_toml = self.julia_env_path(base=False) clean_load = [path for path in dirty_load if not USER_DEPOT_PATTERN.search(path) and path != project_toml] @@ -328,7 +328,7 @@ def load_module(self, *args, **kwargs): else: # In older Julia versions the trailing colon doesn't prevent the user $HOME being added # So use the extra logic to avoid that, see https://github.com/easybuilders/easybuild-easyblocks/pull/4102 - depot_path = os.pathsep.join(self.determine_clean_paths()[0]) + depot_path = os.pathsep.join(self.determine_clean_paths(keep_installdir=True)[0]) # Prepend a temporary directory so the install path is not affected by sanity checks env.setvar('JULIA_DEPOT_PATH', f"{self.tmp_depot_path}:{depot_path}") self.set_pkg_offline() From 7faac3b511d9ad260d9bba52ac94826eb6e0fc4f Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Fri, 1 May 2026 10:22:34 +0200 Subject: [PATCH 11/12] Apply suggestion from @Crivella Co-authored-by: Davide Grassano <34096612+Crivella@users.noreply.github.com> --- easybuild/easyblocks/generic/juliapackage.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index bdad474cb9c..021a6f3ea4b 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -316,6 +316,8 @@ def install_extension(self): def load_module(self, *args, **kwargs): """Set JULIA_DEPOT_PATH excluding the users depot path to avoid writing to $HOME + Also prepend a temporary directory to JULIA_DEPOT_PATH so that sanity check operations + do not write to the installdir DEPOT_PATH Required for e.g. sanity checks that run a julia command. """ From 125342a698ab13e7c56a9af5dfdf6433e14574a5 Mon Sep 17 00:00:00 2001 From: Alexander Grund Date: Mon, 4 May 2026 09:14:44 +0200 Subject: [PATCH 12/12] Keep installdir when cleaning LOAD_PATH --- easybuild/easyblocks/generic/juliapackage.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/easybuild/easyblocks/generic/juliapackage.py b/easybuild/easyblocks/generic/juliapackage.py index 021a6f3ea4b..f442f1a033a 100644 --- a/easybuild/easyblocks/generic/juliapackage.py +++ b/easybuild/easyblocks/generic/juliapackage.py @@ -177,7 +177,8 @@ def determine_clean_paths(self, keep_installdir=False) -> Tuple[List[str], List[ if not USER_DEPOT_PATTERN.search(path) and (keep_installdir or path != self.installdir)] project_toml = self.julia_env_path(base=False) - clean_load = [path for path in dirty_load if not USER_DEPOT_PATTERN.search(path) and path != project_toml] + clean_load = [path for path in dirty_load + if not USER_DEPOT_PATTERN.search(path) and (keep_installdir or path != project_toml)] return clean_depot, clean_load