From b1a36355de66fa9a9557edbef79508f88c763cbb Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Tue, 24 Jan 2023 21:59:41 +0100 Subject: [PATCH 01/24] added a function to obtain full path to a tool --- scripts/utils.sh | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/scripts/utils.sh b/scripts/utils.sh index 5d8455bb68..cd7f758a0d 100644 --- a/scripts/utils.sh +++ b/scripts/utils.sh @@ -31,3 +31,35 @@ function check_exit_code { fatal_error "${fail_msg}" fi } + +function get_path_for_tool { + tool_name=$1 + tool_envvar_name=$2 + + which_out=$(which ${tool_name} 2>&1) + exit_code=$? + if [[ ${exit_code} -eq 0 ]]; then + echo "INFO: found tool ${tool_name} in PATH (${which_out})" >&2 + echo "${which_out}" + return 0 + fi + if [[ -z "${tool_envvar_name}" ]]; then + msg="no env var holding the full path to tool '${tool_name}' provided" + echo "${msg}" >&2 + return 1 + else + tool_envvar_value=${!tool_envvar_name} + if [[ -x "${tool_envvar_value}" ]]; then + msg="INFO: found tool ${tool_envvar_value} via env var ${tool_envvar_name}" + echo "${msg}" >&2 + echo "${tool_envvar_value}" + return 0 + else + msg="ERROR: tool '${tool_name}' not in PATH\n" + msg+="ERROR: tool '${tool_envvar_value}' via '${tool_envvar_name}' not in PATH" + echo "${msg}" >&2 + echo "" + return 2 + fi + fi +} From 27bc2035b00f59442fd46bcdbd6e104c09944f18 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thomas=20R=C3=B6blitz?= Date: Wed, 25 Jan 2023 19:37:55 +0100 Subject: [PATCH 02/24] added function to determine IPv4 address --- scripts/utils.sh | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/scripts/utils.sh b/scripts/utils.sh index cd7f758a0d..db533adc12 100644 --- a/scripts/utils.sh +++ b/scripts/utils.sh @@ -63,3 +63,12 @@ function get_path_for_tool { fi fi } + +function get_ipv4_address { + hname=$1 + hipv4=$(grep ${hname} /etc/hosts | grep -v '^[[:space:]]*#' | cut -d ' ' -f 1) + # TODO try other methods if the one above does not work --> tool that verifies + # what method can be used? + echo "${hipv4}" + return 0 +} From bfe6d36bf056c9e4e9719fa3a8110899fb125dc2 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 20:44:16 +0100 Subject: [PATCH 03/24] various updates for bot/build.sh and eessi_container.sh cherry-picked via commit b5bf008e4136b7877e06ca0602b6fd6aa49128c0 ONLY picked chages to eessi_container.sh --- eessi_container.sh | 103 ++++++++++++++++++++++++--------------------- 1 file changed, 55 insertions(+), 48 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 96a9900a5e..3045fd5a89 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -43,8 +43,8 @@ MODE_UNKNOWN_EXITCODE=$((${ANY_ERROR_EXITCODE} << 5)) REPOSITORY_ERROR_EXITCODE=$((${ANY_ERROR_EXITCODE} << 6)) RESUME_ERROR_EXITCODE=$((${ANY_ERROR_EXITCODE} << 7)) SAVE_ERROR_EXITCODE=$((${ANY_ERROR_EXITCODE} << 8)) -#HTTP_PROXY_ERROR_EXITCODE=$((${ANY_ERROR_EXITCODE} << 9)) -#HTTPS_PROXY_ERROR_EXITCODE=$((${ANY_ERROR_EXITCODE} << 10)) +HTTP_PROXY_ERROR_EXITCODE=$((${ANY_ERROR_EXITCODE} << 9)) +HTTPS_PROXY_ERROR_EXITCODE=$((${ANY_ERROR_EXITCODE} << 10)) RUN_SCRIPT_MISSING_EXITCODE=$((${ANY_ERROR_EXITCODE} << 11)) # CernVM-FS settings @@ -64,39 +64,39 @@ export EESSI_REPOS_CFG_FILE="${EESSI_REPOS_CFG_FILE_OVERRIDE:=repos.cfg}" display_help() { echo "usage: $0 [OPTIONS] [SCRIPT]" echo " OPTIONS:" - echo " -a | --access {ro,rw} - ro (read-only), rw (read & write) [default: ro]" - echo " -c | --container IMG - image file or URL defining the container to use" - echo " [default: docker://ghcr.io/eessi/build-node:debian11]" - echo " -h | --help - display this usage information [default: false]" - echo " -g | --storage DIR - directory space on host machine (used for" - echo " temporary data) [default: 1. TMPDIR, 2. /tmp]" - echo " -m | --mode MODE - with MODE==shell (launch interactive shell) or" - echo " MODE==run (run a script) [default: shell]" - echo " -r | --repository CFG - configuration file or identifier defining the" - echo " repository to use [default: EESSI-pilot via" + echo " -a | --access {ro,rw} - ro (read-only), rw (read & write) [default: ro]" + echo " -c | --container IMG - image file or URL defining the container to use" + echo " [default: docker://ghcr.io/eessi/build-node:debian11]" + echo " -h | --help - display this usage information [default: false]" + echo " -g | --storage DIR - directory space on host machine (used for" + echo " temporary data) [default: 1. TMPDIR, 2. /tmp]" + echo " -m | --mode MODE - with MODE==shell (launch interactive shell) or" + echo " MODE==run (run a script) [default: shell]" + echo " -r | --repository CFG - configuration file or identifier defining the" + echo " repository to use [default: EESSI-pilot via" echo " container configuration]" - echo " -u | --resume DIR/TGZ - resume a previous run from a directory or tarball," - echo " where DIR points to a previously used tmp directory" - echo " (check for output 'Using DIR as tmp ...' of a previous" - echo " run) and TGZ is the path to a tarball which is" - echo " unpacked the tmp dir stored on the local storage space" - echo " (see option --storage above) [default: not set]" - echo " -s | --save DIR/TGZ - save contents of tmp directory to a tarball in" - echo " directory DIR or provided with the fixed full path TGZ" - echo " when a directory is provided, the format of the" - echo " tarball's name will be {REPO_ID}-{TIMESTAMP}.tgz" - echo " [default: not set]" - echo " -v | --verbose - display more information [default: false]" + echo " -u | --resume DIR/TGZ - resume a previous run from a directory or tarball," + echo " where DIR points to a previously used tmp directory" + echo " (check for output 'Using DIR as tmp ...' of a previous" + echo " run) and TGZ is the path to a tarball which is" + echo " unpacked the tmp dir stored on the local storage space" + echo " (see option --storage above) [default: not set]" + echo " -s | --save DIR/TGZ - save contents of tmp directory to a tarball in" + echo " directory DIR or provided with the fixed full path TGZ" + echo " when a directory is provided, the format of the" + echo " tarball's name will be {REPO_ID}-{TIMESTAMP}.tgz" + echo " [default: not set]" + echo " -v | --verbose - display more information [default: false]" + echo " -x | --http-proxy URL - provides URL for the env variable http_proxy" + echo " [default: not set]; uses env var \$http_proxy if set" + echo " -y | --https-proxy URL - provides URL for the env variable https_proxy" + echo " [default: not set]; uses env var \$https_proxy if set" echo echo " If value for --mode is 'run', the SCRIPT provided is executed." - #echo - #echo " FEATURES/OPTIONS to be implemented:" - #echo " -d | --dry-run - run script except for executing the container," - #echo " print information about setup [default: false]" - #echo " -x | --http-proxy URL - provides URL for the env variable http_proxy" - #echo " [default: not set]" - #echo " -y | --https-proxy URL - provides URL for the env variable https_proxy" - #echo " [default: not set]" + echo + echo " FEATURES/OPTIONS to be implemented:" + echo " -d | --dry-run - run script except for executing the container," + echo " print information about setup [default: false]" } # set defaults for command line arguments @@ -109,8 +109,8 @@ MODE="shell" REPOSITORY="EESSI-pilot" RESUME= SAVE= -#HTTP_PROXY= -#HTTPS_PROXY= +HTTP_PROXY=${http_proxy:-} +HTTPS_PROXY=${https_proxy:-} POSITIONAL_ARGS=() @@ -156,16 +156,16 @@ while [[ $# -gt 0 ]]; do VERBOSE=1 shift 1 ;; -# -x|--http-proxy) -# HTTP_PROXY="$2" -# export http_proxy=${HTTP_PROXY} -# shift 2 -# ;; -# -y|--https-proxy) -# HTTPS_PROXY="$2" -# export https_proxy=${HTTPS_PROXY} -# shift 2 -# ;; + -x|--http-proxy) + HTTP_PROXY="$2" + export http_proxy=${HTTP_PROXY} + shift 2 + ;; + -y|--https-proxy) + HTTPS_PROXY="$2" + export https_proxy=${HTTPS_PROXY} + shift 2 + ;; -*|--*) fatal_error "Unknown option: $1" "${CMDLINE_ARG_UNKNOWN_EXITCODE}" ;; @@ -311,9 +311,9 @@ BIND_PATHS="${EESSI_CVMFS_VAR_LIB}:/var/lib/cvmfs,${EESSI_CVMFS_VAR_RUN}:/var/ru BIND_PATHS="${BIND_PATHS},${EESSI_TMPDIR}:/tmp" [[ ${VERBOSE} -eq 1 ]] && echo "BIND_PATHS=${BIND_PATHS}" -# set up repository config (always create cfg dir and populate it with info when +# set up repository config (always create directory repos_cfg and populate it with info when # arg -r|--repository is used) -mkdir -p ${EESSI_TMPDIR}/cfg +mkdir -p ${EESSI_TMPDIR}/repos_cfg if [[ "${REPOSITORY}" == "EESSI-pilot" ]]; then # need to source defaults as late as possible (see other sourcing below) source ${TOPDIR}/init/eessi_defaults @@ -370,13 +370,13 @@ else # only unpack config_bundle if we're not resuming from a previous run if [[ -z ${RESUME} ]]; then - tar xf ${config_bundle} -C ${EESSI_TMPDIR}/cfg + tar xf ${config_bundle} -C ${EESSI_TMPDIR}/repos_cfg fi for src in "${!cfg_file_map[@]}" do target=${cfg_file_map[${src}]} - BIND_PATHS="${BIND_PATHS},${EESSI_TMPDIR}/cfg/${src}:${target}" + BIND_PATHS="${BIND_PATHS},${EESSI_TMPDIR}/repos_cfg/${src}:${target}" done export EESSI_PILOT_VERSION_OVERRIDE=${repo_version} export EESSI_CVMFS_REPO_OVERRIDE="/cvmfs/${repo_name}" @@ -432,6 +432,13 @@ else fi [[ ${VERBOSE} -eq 1 ]] && echo "SINGULARITY_BIND=${SINGULARITY_BIND}" +# pass $EESSI_SOFTWARE_SUBDIR_OVERRIDE into build container (if set) +if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then + export SINGULARITYENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} + # also specify via $APPTAINERENV_* (future proof, cfr. https://apptainer.org/docs/user/latest/singularity_compatibility.html#singularity-environment-variable-compatibility) + export APPTAINERENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} +fi + echo "Launching container with command (next line):" echo "singularity ${MODE} ${EESSI_FUSE_MOUNTS[@]} ${CONTAINER} $@" # TODO for now we run singularity with '-q' (quiet), later adjust this to the log level From 837234107d28cd9b2d759a66af8f7e2ec5244923 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 20:55:30 +0100 Subject: [PATCH 04/24] provide CVMFS_HTTP_PROXY if necessary cherry-picked via commit b5c07eeb99e77191d818e64788b0d419031cf526 NOTE, only applied changes to eessi_container.sh --- eessi_container.sh | 39 ++++++++++++++++++++++++++++----------- 1 file changed, 28 insertions(+), 11 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 3045fd5a89..9238d3c793 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -24,8 +24,8 @@ # 2. set up host storage/tmp # 3. set up common vars and directories # 4. set up vars specific to a scenario -# 5. initialize host storage/tmp from previous run if provided -# 6. run container +# 5. run container +# 6. save tmp (if requested) # -. initial settings & exit codes TOPDIR=$(dirname $(realpath $0)) @@ -279,7 +279,7 @@ fi # |-overlay-upper # |-overlay-work # |-home -# |-cfg +# |-repos_cfg # tmp dir for EESSI EESSI_TMPDIR=${EESSI_HOST_STORAGE} @@ -361,9 +361,9 @@ else cfg_init_file_map "${config_map}" [[ ${VERBOSE} -eq 1 ]] && cfg_print_map - # TODO use information to set up dir ${EESSI_TMPDIR}/cfg, - # define BIND mounts and override repo name and version - # check if config_bundle exists, if so, unpack it into ${EESSI_TMPDIR}/cfg + # use information to set up dir ${EESSI_TMPDIR}/repos_cfg, + # define BIND mounts and override repo name and version + # check if config_bundle exists, if so, unpack it into ${EESSI_TMPDIR}/repos_cfg if [[ ! -r ${config_bundle} ]]; then fatal_error "config bundle '${config_bundle}' is not readable" ${REPOSITORY_ERROR_EXITCODE} fi @@ -384,6 +384,26 @@ else source ${TOPDIR}/init/eessi_defaults fi +# if http_proxy is not empty, we assume that the machine accesses internet +# via a proxy. then we need to add CVMFS_HTTP_PROXY to +# ${EESSI_TMPDIR}/repos_cfg/default.local on host (and possibly add a BIND +# MOUNT if it was not yet in BIND_PATHS) +if [[ ! -z ${http_proxy} ]]; then + # TODO tolerate other formats for proxy URLs, for now assume format is + # http://SOME_HOSTNAME:SOME_PORT + PROXY_HOST_AND_PORT=${http_proxy#http:\/\//} # strip http:// + PROXY_PORT=${PROXY_HOST_AND_PORT#.*:/} # remove hostname: to get port + HTTP_PROXY_HOSTNAME=${PROXY_HOST_AND_PORT%:${PROX_PORT}/} + HTTP_PROXY_IPV4=$(get_ipv4_address ${HTTP_PROXY_HOSTNAME}) + echo "CVMFS_HTTP_PROXY=\"${http_proxy}|" \ + "http://${HTTP_PROXY_IPV4}:${PROXY_PORT}\"" \ + >> ${EESSI_TMPDIR}/repos_cfg/default.local + cat ${EESSI_TMPDIR}/repos_cfg/default.local + # if default.local is not BIND mounted into container, add it to BIND_PATHS + if [[ ${BIND_PATHS} !~ "${EESSI_TMPDIR}/repos_cfg/default.local:/etc/cvmfs/default.local" ]]; then + export BIND_PATHS="${BIND_PATHS},${EESSI_TMPDIR}/repos_cfg/default.local:/etc/cvmfs/default.local" + fi +fi # 4. set up vars and dirs specific to a scenario @@ -420,10 +440,7 @@ if [[ "${ACCESS}" == "rw" ]]; then fi -# 5. initialize host storage/tmp from previous run if provided - - -# 6. run container +# 5. run container # final settings if [[ -z ${SINGULARITY_BIND} ]]; then export SINGULARITY_BIND="${BIND_PATHS}" @@ -446,7 +463,7 @@ echo "singularity ${MODE} ${EESSI_FUSE_MOUNTS[@]} ${CONTAINER} $@" singularity -q ${MODE} "${EESSI_FUSE_MOUNTS[@]}" ${CONTAINER} "$@" exit_code=$? -# 7. save tmp if requested (arg -s|--save) +# 6. save tmp if requested (arg -s|--save) if [[ ! -z ${SAVE} ]]; then # Note, for now we don't try to be smart and record in any way the OS and # ARCH which might have been used internally, eg, when software packages From 3f1aed9a2b5da7fa7e017e415d24a412dbfa18fc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thomas=20R=C3=B6blitz?= Date: Fri, 27 Jan 2023 22:41:36 +0100 Subject: [PATCH 05/24] add functions to derive hostname and port number from proxy URL --- scripts/utils.sh | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/scripts/utils.sh b/scripts/utils.sh index db533adc12..fb4eff1e3f 100644 --- a/scripts/utils.sh +++ b/scripts/utils.sh @@ -64,6 +64,30 @@ function get_path_for_tool { fi } +function get_host_from_url { + url=$1 + re="(http|https)://([^/:]+)" + if [[ $url =~ $re ]]; then + echo ${BASH_REMATCH[2]} + return 0 + else + echo "" + return 1 + fi +} + +function get_port_from_url { + url=$1 + re="(http|https)://[^:]+:([0-9]+)" + if [[ $url =~ $re ]]; then + echo ${BASH_REMATCH[2]} + return 0 + else + echo "" + return 1 + fi +} + function get_ipv4_address { hname=$1 hipv4=$(grep ${hname} /etc/hosts | grep -v '^[[:space:]]*#' | cut -d ' ' -f 1) From b7abfc6e7de85e2b46e3241d8946a1211dcde568 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thomas=20R=C3=B6blitz?= Date: Fri, 27 Jan 2023 22:43:27 +0100 Subject: [PATCH 06/24] add function to determine config sections --- cfg_files.sh | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/cfg_files.sh b/cfg_files.sh index 885ebd0877..ffd29db50a 100644 --- a/cfg_files.sh +++ b/cfg_files.sh @@ -47,9 +47,7 @@ function cfg_load { else val=$(cfg_get_key_value $line) # trim leading and trailing spaces as well - #cur_key=$(echo $val | cut -f1 -d'=' | sed -e 's/^[[:space:]]*//' | sed -e 's/[[:space:]]*$//') cur_key=$(echo $val | cut -f1 -d'=' | cfg_trim_spaces) - #cur_val=$(echo $val | cut -f2 -d'=' | sed -e 's/^[[:space:]]*//' | sed -e 's/[[:space:]]*$//') cur_val=$(echo $val | cut -f2 -d'=' | cfg_trim_spaces) if [[ -n "$cur_key" ]]; then # section + key is the associative in bash array, the field separator is space @@ -69,6 +67,20 @@ function cfg_print { done } +function cfg_sections { + declare -A sections + for key in "${!cfg_repos[@]}" + do + # extract section from the associative key + section=$(echo $key | cut -f1 -d ' ') + sections[${section}]=1 + done + for repo in "${!sections[@]}" + do + echo "${repo}" + done +} + function cfg_get_value { section=$1 key=$2 From 9b7b8a4db00261b0fe2bd40152d7adacde11ffe3 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 21:17:11 +0100 Subject: [PATCH 07/24] add parameter to list repositories, fix bugs fixed bugs - determining IP address for proxy host was wrong - handling of positional parameters for executing commands with arguments was wrong --- eessi_container.sh | 36 ++++++++++++++++++++++++++++-------- 1 file changed, 28 insertions(+), 8 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 9238d3c793..06b77a5acf 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -70,6 +70,7 @@ display_help() { echo " -h | --help - display this usage information [default: false]" echo " -g | --storage DIR - directory space on host machine (used for" echo " temporary data) [default: 1. TMPDIR, 2. /tmp]" + echo " -l | --list-repos - list available repository identifiers [default: false]" echo " -m | --mode MODE - with MODE==shell (launch interactive shell) or" echo " MODE==run (run a script) [default: shell]" echo " -r | --repository CFG - configuration file or identifier defining the" @@ -105,6 +106,7 @@ CONTAINER="docker://ghcr.io/eessi/build-node:debian11" #DRY_RUN=0 VERBOSE=0 STORAGE= +LIST_REPOS=0 MODE="shell" REPOSITORY="EESSI-pilot" RESUME= @@ -136,6 +138,10 @@ while [[ $# -gt 0 ]]; do display_help exit 0 ;; + -l|--list-repos) + LIST_REPOS=1 + shift 1 + ;; -m|--mode) MODE="$2" shift 2 @@ -178,6 +184,17 @@ done set -- "${POSITIONAL_ARGS[@]}" +if [[ ${LIST_REPOS} -eq 1 ]]; then + echo "Repositories defined in the config file '${EESSI_REPOS_CFG_FILE}':" + echo " EESSI-pilot [default]" + cfg_load ${EESSI_REPOS_CFG_FILE} + sections=$(cfg_sections) + while IFS= read -r repo_id + do + echo " ${repo_id}" + done <<< "${sections}" + exit 0 +fi # 1. check if argument values are valid # (arg -a|--access) check if ACCESS is supported @@ -390,17 +407,20 @@ fi # MOUNT if it was not yet in BIND_PATHS) if [[ ! -z ${http_proxy} ]]; then # TODO tolerate other formats for proxy URLs, for now assume format is - # http://SOME_HOSTNAME:SOME_PORT - PROXY_HOST_AND_PORT=${http_proxy#http:\/\//} # strip http:// - PROXY_PORT=${PROXY_HOST_AND_PORT#.*:/} # remove hostname: to get port - HTTP_PROXY_HOSTNAME=${PROXY_HOST_AND_PORT%:${PROX_PORT}/} - HTTP_PROXY_IPV4=$(get_ipv4_address ${HTTP_PROXY_HOSTNAME}) - echo "CVMFS_HTTP_PROXY=\"${http_proxy}|" \ - "http://${HTTP_PROXY_IPV4}:${PROXY_PORT}\"" \ + # http://SOME_HOSTNAME:SOME_PORT/ + [[ ${VERBOSE} -eq 1 ]] && echo "http_proxy='${http_proxy}'" + PROXY_HOST=$(get_host_from_url ${http_proxy}) + [[ ${VERBOSE} -eq 1 ]] && echo "PROXY_HOST='${PROXY_HOST}'" + PROXY_PORT=$(get_port_from_url ${http_proxy}) + [[ ${VERBOSE} -eq 1 ]] && echo "PROXY_PORT='${PROXY_PORT}'" + HTTP_PROXY_IPV4=$(get_ipv4_address ${PROXY_HOST}) + [[ ${VERBOSE} -eq 1 ]] && echo "HTTP_PROXY_IPV4='${HTTP_PROXY_IPV4}'" + echo "CVMFS_HTTP_PROXY=\"${http_proxy}|http://${HTTP_PROXY_IPV4}:${PROXY_PORT}\"" \ >> ${EESSI_TMPDIR}/repos_cfg/default.local cat ${EESSI_TMPDIR}/repos_cfg/default.local + # if default.local is not BIND mounted into container, add it to BIND_PATHS - if [[ ${BIND_PATHS} !~ "${EESSI_TMPDIR}/repos_cfg/default.local:/etc/cvmfs/default.local" ]]; then + if [[ ! ${BIND_PATHS} =~ "${EESSI_TMPDIR}/repos_cfg/default.local:/etc/cvmfs/default.local" ]]; then export BIND_PATHS="${BIND_PATHS},${EESSI_TMPDIR}/repos_cfg/default.local:/etc/cvmfs/default.local" fi fi From 4a414f593d6ff02629d1374e67006dcd1a85f71c Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 21:26:19 +0100 Subject: [PATCH 08/24] replace FILE with DIR in EESSI_REPOS_CFG_FILE_OVERRIDE NOTE only applied changes to eessi_container.sh --- eessi_container.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 06b77a5acf..d59bb38687 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -52,8 +52,8 @@ CVMFS_VAR_LIB="var-lib-cvmfs" CVMFS_VAR_RUN="var-run-cvmfs" # repository cfg file, default name (default location: $PWD) -# can be overwritten by setting env var EESSI_REPOS_CFG_FILE_OVERRIDE -export EESSI_REPOS_CFG_FILE="${EESSI_REPOS_CFG_FILE_OVERRIDE:=repos.cfg}" +# can be overwritten by setting env var EESSI_REPOS_CFG_DIR_OVERRIDE +export EESSI_REPOS_CFG_FILE="${EESSI_REPOS_CFG_DIR_OVERRIDE:=.}/repos.cfg" # 0. parse args From 37abf4f8aab9d138ad763cd457d2476bef16a6aa Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sun, 29 Jan 2023 19:56:41 +0100 Subject: [PATCH 09/24] fix whitespace issues --- cfg_files.sh | 1 - eessi_container.sh | 2 +- init/eessi_defaults | 1 - scripts/utils.sh | 4 ++-- 4 files changed, 3 insertions(+), 5 deletions(-) diff --git a/cfg_files.sh b/cfg_files.sh index ffd29db50a..57ea2f7c03 100644 --- a/cfg_files.sh +++ b/cfg_files.sh @@ -165,4 +165,3 @@ function cfg_print_map { echo "${index} --> ${cfg_file_map[${index}]}" done } - diff --git a/eessi_container.sh b/eessi_container.sh index d59bb38687..1a2e61227b 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -413,7 +413,7 @@ if [[ ! -z ${http_proxy} ]]; then [[ ${VERBOSE} -eq 1 ]] && echo "PROXY_HOST='${PROXY_HOST}'" PROXY_PORT=$(get_port_from_url ${http_proxy}) [[ ${VERBOSE} -eq 1 ]] && echo "PROXY_PORT='${PROXY_PORT}'" - HTTP_PROXY_IPV4=$(get_ipv4_address ${PROXY_HOST}) + HTTP_PROXY_IPV4=$(get_ipv4_address ${PROXY_HOST}) [[ ${VERBOSE} -eq 1 ]] && echo "HTTP_PROXY_IPV4='${HTTP_PROXY_IPV4}'" echo "CVMFS_HTTP_PROXY=\"${http_proxy}|http://${HTTP_PROXY_IPV4}:${PROXY_PORT}\"" \ >> ${EESSI_TMPDIR}/repos_cfg/default.local diff --git a/init/eessi_defaults b/init/eessi_defaults index 1b5ce07fb1..f482cbc269 100644 --- a/init/eessi_defaults +++ b/init/eessi_defaults @@ -10,4 +10,3 @@ export EESSI_CVMFS_REPO="${EESSI_CVMFS_REPO_OVERRIDE:=/cvmfs/pilot.eessi-hpc.org}" export EESSI_PILOT_VERSION="${EESSI_PILOT_VERSION_OVERRIDE:=2021.12}" - diff --git a/scripts/utils.sh b/scripts/utils.sh index fb4eff1e3f..d0da95e87f 100644 --- a/scripts/utils.sh +++ b/scripts/utils.sh @@ -73,7 +73,7 @@ function get_host_from_url { else echo "" return 1 - fi + fi } function get_port_from_url { @@ -85,7 +85,7 @@ function get_port_from_url { else echo "" return 1 - fi + fi } function get_ipv4_address { From d468a1ababa8072c4069917f4c16529cd362011f Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 21:42:34 +0100 Subject: [PATCH 10/24] include changes made to test PR for building with the bot cherry-picked via commit fce504fb466be005f1d417e96e47f442c8f29c52 NOTE, only changed eessi_container.sh --- eessi_container.sh | 50 ++++++++++++++++++++++++++++++++-------------- 1 file changed, 35 insertions(+), 15 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 1a2e61227b..14fb716abb 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -51,9 +51,15 @@ RUN_SCRIPT_MISSING_EXITCODE=$((${ANY_ERROR_EXITCODE} << 11)) CVMFS_VAR_LIB="var-lib-cvmfs" CVMFS_VAR_RUN="var-run-cvmfs" +# directory for tmp used inside container +export TMP_IN_CONTAINER=/tmp + # repository cfg file, default name (default location: $PWD) # can be overwritten by setting env var EESSI_REPOS_CFG_DIR_OVERRIDE -export EESSI_REPOS_CFG_FILE="${EESSI_REPOS_CFG_DIR_OVERRIDE:=.}/repos.cfg" +export EESSI_REPOS_CFG_FILE="${EESSI_REPOS_CFG_DIR_OVERRIDE:=${PWD}}/repos.cfg" +# other repository cfg files in directory, default location: $PWD +# can be overwritten by setting env var EESSI_REPOS_CFG_DIR_OVERRIDE +export EESSI_REPOS_CFG_DIR="${EESSI_REPOS_CFG_DIR_OVERRIDE:=${PWD}}" # 0. parse args @@ -199,7 +205,7 @@ fi # 1. check if argument values are valid # (arg -a|--access) check if ACCESS is supported if [[ "${ACCESS}" != "ro" && "${ACCESS}" != "rw" ]]; then - fatal_error "unknown access method '${ACCESS}'" "${ACCESS_UNKNOWN_EXITCODE}" + fatal_error "unknown access method '${ACCESS}'" "${ACCESS_UNKNOWN_EXITCODE}" fi # TODO (arg -c|--container) check container (is it a file or URL & access those) @@ -211,11 +217,14 @@ fi # (arg -m|--mode) check if MODE is known if [[ "${MODE}" != "shell" && "${MODE}" != "run" ]]; then - fatal_error "unknown execution mode '${MODE}'" "${MODE_UNKNOWN_EXITCODE}" + fatal_error "unknown execution mode '${MODE}'" "${MODE_UNKNOWN_EXITCODE}" fi # TODO (arg -r|--repository) check if repository is known # REPOSITORY_ERROR_EXITCODE +if [[ ! -z "${REPOSITORY}" && "${REPOSITORY}" != "EESSI-pilot" && ! -r ${EESSI_REPOS_CFG_FILE} ]]; then + fatal_error "arg '--repository ${REPOSITORY}' requires a cfg file at '${EESSI_REPOS_CFG_FILE}'" "${REPOSITORY_ERROR_EXITCODE}" +fi # TODO (arg -u|--resume) check if it exists, if user has read permission, # if it contains data from a previous run @@ -249,6 +258,7 @@ if [[ ! -z ${RESUME} && -d ${RESUME} ]]; then # skip creating a new tmp directory, just set environment variables echo "Resuming from previous run using temporary storage at ${RESUME}" EESSI_HOST_STORAGE=${RESUME} + echo "RESUME_FROM_DIR ${EESSI_HOST_STORAGE}" else # we need a tmp location (and possibly init it with ${RESUME} if it was not # a directory @@ -325,7 +335,9 @@ fi # define paths to add to SINGULARITY_BIND (added later when all BIND mounts are defined) BIND_PATHS="${EESSI_CVMFS_VAR_LIB}:/var/lib/cvmfs,${EESSI_CVMFS_VAR_RUN}:/var/run/cvmfs" -BIND_PATHS="${BIND_PATHS},${EESSI_TMPDIR}:/tmp" +# provide a '/tmp' inside the container +BIND_PATHS="${BIND_PATHS},${EESSI_TMPDIR}:${TMP_IN_CONTAINER}" + [[ ${VERBOSE} -eq 1 ]] && echo "BIND_PATHS=${BIND_PATHS}" # set up repository config (always create directory repos_cfg and populate it with info when @@ -381,13 +393,22 @@ else # use information to set up dir ${EESSI_TMPDIR}/repos_cfg, # define BIND mounts and override repo name and version # check if config_bundle exists, if so, unpack it into ${EESSI_TMPDIR}/repos_cfg - if [[ ! -r ${config_bundle} ]]; then - fatal_error "config bundle '${config_bundle}' is not readable" ${REPOSITORY_ERROR_EXITCODE} + # if config_bundle is relative path (no '/' at start) prepend it with + # EESSI_REPOS_CFG_DIR + config_bundle_path= + if [[ ! "${config_bundle}" =~ ^/ ]]; then + config_bundle_path=${EESSI_REPOS_CFG_DIR}/${config_bundle} + else + config_bundle_path=${config_bundle} + fi + + if [[ ! -r ${config_bundle_path} ]]; then + fatal_error "config bundle '${config_bundle_path}' is not readable" ${REPOSITORY_ERROR_EXITCODE} fi # only unpack config_bundle if we're not resuming from a previous run if [[ -z ${RESUME} ]]; then - tar xf ${config_bundle} -C ${EESSI_TMPDIR}/repos_cfg + tar xf ${config_bundle_path} -C ${EESSI_TMPDIR}/repos_cfg fi for src in "${!cfg_file_map[@]}" @@ -436,12 +457,8 @@ if [[ "${ACCESS}" == "ro" ]]; then fi if [[ "${ACCESS}" == "rw" ]]; then - EESSI_CVMFS_OVERLAY_UPPER=/tmp/overlay-upper - EESSI_CVMFS_OVERLAY_WORK=/tmp/overlay-work mkdir -p ${EESSI_TMPDIR}/overlay-upper mkdir -p ${EESSI_TMPDIR}/overlay-work - [[ ${VERBOSE} -eq 1 ]] && echo "EESSI_CVMFS_OVERLAY_UPPER=${EESSI_CVMFS_OVERLAY_UPPER}" - [[ ${VERBOSE} -eq 1 ]] && echo "EESSI_CVMFS_OVERLAY_WORK=${EESSI_CVMFS_OVERLAY_WORK}" # set environment variables for fuse mounts in Singularity container export EESSI_PILOT_READONLY="container:cvmfs2 ${repo_name} /cvmfs_ro/${repo_name}" @@ -450,8 +467,8 @@ if [[ "${ACCESS}" == "rw" ]]; then EESSI_PILOT_WRITABLE_OVERLAY="container:fuse-overlayfs" EESSI_PILOT_WRITABLE_OVERLAY+=" -o lowerdir=/cvmfs_ro/${repo_name}" - EESSI_PILOT_WRITABLE_OVERLAY+=" -o upperdir=/tmp/overlay-upper" - EESSI_PILOT_WRITABLE_OVERLAY+=" -o workdir=/tmp/overlay-work" + EESSI_PILOT_WRITABLE_OVERLAY+=" -o upperdir=${TMP_IN_CONTAINER}/overlay-upper" + EESSI_PILOT_WRITABLE_OVERLAY+=" -o workdir=${TMP_IN_CONTAINER}/overlay-work" EESSI_PILOT_WRITABLE_OVERLAY+=" ${EESSI_CVMFS_REPO}" export EESSI_PILOT_WRITABLE_OVERLAY @@ -476,11 +493,13 @@ if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then export APPTAINERENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} fi +# if INFO is set to 1 (arg --info), add argument '-q' +RUN_QUIET=${INFO:--q} echo "Launching container with command (next line):" -echo "singularity ${MODE} ${EESSI_FUSE_MOUNTS[@]} ${CONTAINER} $@" +echo "singularity ${RUN_QUIET} ${MODE} ${EESSI_FUSE_MOUNTS[@]} ${CONTAINER} $@" # TODO for now we run singularity with '-q' (quiet), later adjust this to the log level # provided to the script -singularity -q ${MODE} "${EESSI_FUSE_MOUNTS[@]}" ${CONTAINER} "$@" +singularity ${RUN_QUIET} ${MODE} "${EESSI_FUSE_MOUNTS[@]}" ${CONTAINER} "$@" exit_code=$? # 6. save tmp if requested (arg -s|--save) @@ -500,6 +519,7 @@ if [[ ! -z ${SAVE} ]]; then fi tar cf ${TGZ} -C ${EESSI_TMPDIR} . echo "Saved contents of '${EESSI_TMPDIR}' to '${TGZ}' (to resume, add '--resume ${TGZ}')" + echo "RESUME_FROM_TGZ ${TGZ}" fi # TODO clean up tmp by default? only retain if another option provided (--retain-tmp) From af658ee9229f36eac972bef87a36bbb6b883ef48 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Fri, 3 Feb 2023 20:58:01 +0100 Subject: [PATCH 11/24] fix issues in eessi_container.sh --- eessi_container.sh | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 14fb716abb..23118d0d72 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -258,7 +258,6 @@ if [[ ! -z ${RESUME} && -d ${RESUME} ]]; then # skip creating a new tmp directory, just set environment variables echo "Resuming from previous run using temporary storage at ${RESUME}" EESSI_HOST_STORAGE=${RESUME} - echo "RESUME_FROM_DIR ${EESSI_HOST_STORAGE}" else # we need a tmp location (and possibly init it with ${RESUME} if it was not # a directory @@ -290,6 +289,7 @@ else EESSI_HOST_STORAGE=$(mktemp -d --tmpdir eessi.XXXXXXXXXX) echo "Using ${EESSI_HOST_STORAGE} as tmp storage (add '--resume ${EESSI_HOST_STORAGE}' to resume where this session ended)." fi +echo "RESUME_FROM_DIR ${EESSI_HOST_STORAGE}" # if ${RESUME} is a file (assume a tgz), unpack it into ${EESSI_HOST_STORAGE} if [[ ! -z ${RESUME} && -f ${RESUME} ]]; then @@ -494,7 +494,12 @@ if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then fi # if INFO is set to 1 (arg --info), add argument '-q' -RUN_QUIET=${INFO:--q} +if [[ -z ${INFO} ]]; then + RUN_QUIET='-q' +else + RUN_QUIET='' +fi + echo "Launching container with command (next line):" echo "singularity ${RUN_QUIET} ${MODE} ${EESSI_FUSE_MOUNTS[@]} ${CONTAINER} $@" # TODO for now we run singularity with '-q' (quiet), later adjust this to the log level From eb66e1c4361f458114d2186a846fa9fe56b1df16 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thomas=20R=C3=B6blitz?= Date: Sat, 4 Feb 2023 15:07:23 +0100 Subject: [PATCH 12/24] fix RUN_QUIET setting --- eessi_container.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 23118d0d72..89d4bd98f6 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -493,8 +493,8 @@ if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then export APPTAINERENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} fi -# if INFO is set to 1 (arg --info), add argument '-q' -if [[ -z ${INFO} ]]; then +# if INFO is set to 0 (no arg --info), add argument '-q' +if [[ ${INFO} -eq 0 ]]; then RUN_QUIET='-q' else RUN_QUIET='' From 1cb4674978bee259253330d769ca220ad795202a Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 21:59:39 +0100 Subject: [PATCH 13/24] improvements to resuming job environment cherry-picked via commit 23e773ce0d8c6504e1440629a4178318265b73d2 NOTE only applied changes to eessi_container.sh --- eessi_container.sh | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 89d4bd98f6..e714f8e2d0 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -360,6 +360,9 @@ else # standard EESSI repositories) cfg_load ${EESSI_REPOS_CFG_FILE} + # copy repos.cfg to job directory --> makes it easier to inspect the job + cp ${EESSI_REPOS_CFG_FILE} ${EESSI_TMPDIR}/repos_cfg/. + # cfg file should include: repo_name, repo_version, config_bundle, # map { local_filepath -> container_filepath } # @@ -493,8 +496,8 @@ if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then export APPTAINERENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} fi -# if INFO is set to 0 (no arg --info), add argument '-q' -if [[ ${INFO} -eq 0 ]]; then +# if INFO is set to 1 (arg --info), add argument '-q' +if [[ -z ${INFO} ]]; then RUN_QUIET='-q' else RUN_QUIET='' From 0c465da3de12ed1bb7494651031d64d7f17928e4 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Tue, 7 Feb 2023 19:27:07 +0100 Subject: [PATCH 14/24] address requested change --- eessi_container.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index e714f8e2d0..e8698cd719 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -496,8 +496,8 @@ if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then export APPTAINERENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} fi -# if INFO is set to 1 (arg --info), add argument '-q' -if [[ -z ${INFO} ]]; then +# if INFO is set to 0 (no arg --info), add argument '-q' +if [[ ${INFO} -eq 0 ]]; then RUN_QUIET='-q' else RUN_QUIET='' From 26ab98c1f1cc901d6905424c9fdb2f5c9395ed79 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 22:16:36 +0100 Subject: [PATCH 15/24] cleaning up leftovers after adding updates from NESSI --- eessi_container.sh | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index e8698cd719..e7ad625a15 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -100,10 +100,6 @@ display_help() { echo " [default: not set]; uses env var \$https_proxy if set" echo echo " If value for --mode is 'run', the SCRIPT provided is executed." - echo - echo " FEATURES/OPTIONS to be implemented:" - echo " -d | --dry-run - run script except for executing the container," - echo " print information about setup [default: false]" } # set defaults for command line arguments @@ -496,8 +492,8 @@ if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then export APPTAINERENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} fi -# if INFO is set to 0 (no arg --info), add argument '-q' -if [[ ${INFO} -eq 0 ]]; then +# if VERBOSE is set to 0 (no arg --verbose), add argument '-q' +if [[ ${VERBOSE} -eq 0 ]]; then RUN_QUIET='-q' else RUN_QUIET='' @@ -505,8 +501,6 @@ fi echo "Launching container with command (next line):" echo "singularity ${RUN_QUIET} ${MODE} ${EESSI_FUSE_MOUNTS[@]} ${CONTAINER} $@" -# TODO for now we run singularity with '-q' (quiet), later adjust this to the log level -# provided to the script singularity ${RUN_QUIET} ${MODE} "${EESSI_FUSE_MOUNTS[@]}" ${CONTAINER} "$@" exit_code=$? From a44088e4c33694c0047a6e5874df780e3c2ff15e Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Sat, 18 Feb 2023 22:21:42 +0100 Subject: [PATCH 16/24] moving cfg_files.sh to scripts dir --- eessi_container.sh | 2 +- cfg_files.sh => scripts/cfg_files.sh | 0 2 files changed, 1 insertion(+), 1 deletion(-) rename cfg_files.sh => scripts/cfg_files.sh (100%) diff --git a/eessi_container.sh b/eessi_container.sh index e7ad625a15..6d3fbc0adc 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -31,7 +31,7 @@ TOPDIR=$(dirname $(realpath $0)) source ${TOPDIR}/scripts/utils.sh -source ${TOPDIR}/cfg_files.sh +source ${TOPDIR}/scripts/cfg_files.sh # exit codes: bitwise shift codes to allow for combination of exit codes # ANY_ERROR_EXITCODE is sourced from ${TOPDIR}/scripts/utils.sh diff --git a/cfg_files.sh b/scripts/cfg_files.sh similarity index 100% rename from cfg_files.sh rename to scripts/cfg_files.sh From bbbad0dce469299e4168a54a939facc4c1be7c60 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Mon, 20 Feb 2023 10:07:03 +0100 Subject: [PATCH 17/24] improved handling of container cache + explicit pull of image cherry-picked via commit bfb1b29103dc309a12573f3ec9c247d432f08f73 Note, only part for eessi_container.sh included here --- eessi_container.sh | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 6d3fbc0adc..cdd2c017fb 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -310,10 +310,23 @@ mkdir -p ${EESSI_TMPDIR} [[ ${VERBOSE} -eq 1 ]] && echo "EESSI_TMPDIR=${EESSI_TMPDIR}" # configure Singularity -export SINGULARITY_CACHEDIR=${EESSI_TMPDIR}/singularity_cache -mkdir -p ${SINGULARITY_CACHEDIR} +if [[ -z ${SINGULARITY_CACHEDIR} ]]; then + export SINGULARITY_CACHEDIR=${EESSI_TMPDIR}/singularity_cache + mkdir -p ${SINGULARITY_CACHEDIR} +fi [[ ${VERBOSE} -eq 1 ]] && echo "SINGULARITY_CACHEDIR=${SINGULARITY_CACHEDIR}" +# pull & convert image and reset CONTAINER +CONTAINER_URL_FMT=".*://(.*)" +if [[ ${CONTAINER} == ${CONTAINER_URL_FMT} ]]; then + CONTAINER_IMG=${BASH_REMATCH[1]//[:-]/_}.sif + singularity pull ${CONTAINER_IMG} ${CONTAINER} + if [[ -x ${CONTAINER_IMG} ]]; then + CONTAINER="${PWD}/${CONTAINER_IMG}" + fi +fi +[[ ${INFO} -eq 1 ]] && echo "CONTAINER='${CONTAINER}'" + # set env vars and create directories for CernVM-FS EESSI_CVMFS_VAR_LIB=${EESSI_TMPDIR}/${CVMFS_VAR_LIB} EESSI_CVMFS_VAR_RUN=${EESSI_TMPDIR}/${CVMFS_VAR_RUN} @@ -326,8 +339,8 @@ mkdir -p ${EESSI_CVMFS_VAR_RUN} if [[ -z ${SINGULARITY_HOME} ]]; then export SINGULARITY_HOME="${EESSI_TMPDIR}/home:/home/${USER}" mkdir -p ${EESSI_TMPDIR}/home - [[ ${VERBOSE} -eq 1 ]] && echo "SINGULARITY_HOME=${SINGULARITY_HOME}" fi +[[ ${VERBOSE} -eq 1 ]] && echo "SINGULARITY_HOME=${SINGULARITY_HOME}" # define paths to add to SINGULARITY_BIND (added later when all BIND mounts are defined) BIND_PATHS="${EESSI_CVMFS_VAR_LIB}:/var/lib/cvmfs,${EESSI_CVMFS_VAR_RUN}:/var/run/cvmfs" From 15ae58df240b1b1396611ee6fb5b5dbd50d4e793 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Mon, 20 Feb 2023 10:30:17 +0100 Subject: [PATCH 18/24] use VERBOSE instead of INFO --- .../workflows/test_eessi_container_script.yml | 22 +++++++++++++++++++ eessi_container.sh | 2 +- 2 files changed, 23 insertions(+), 1 deletion(-) diff --git a/.github/workflows/test_eessi_container_script.yml b/.github/workflows/test_eessi_container_script.yml index 7678aedc64..5a44bae155 100644 --- a/.github/workflows/test_eessi_container_script.yml +++ b/.github/workflows/test_eessi_container_script.yml @@ -11,6 +11,8 @@ jobs: matrix: SCRIPT_TEST: - help + - listrepos_default + - listrepos_custom - run - shell - container @@ -39,6 +41,26 @@ jobs: if [[ ${{matrix.SCRIPT_TEST}} == 'help' ]]; then ./eessi_container.sh --help + # test use of --list-repos without custom repos.cfg + elif [[ ${{matrix.SCRIPT_TEST}} == 'listrepos_default' ]]; then + outfile=out_listrepos.txt + ./eessi_container.sh --verbose --list-repos | tee ${outfile} + grep "EESSI-pilot" ${outfile} + + # test use of --list-repos with custom repos.cfg + elif [[ ${{matrix.SCRIPT_TEST}} == 'listrepos_custom' ]]; then + outfile=out_listrepos.txt + outfile2=out_listrepos_2.txt + mkdir -p ${PWD}/cfg + echo "[EESSI/2021.12]" > cfg/repos.cfg + echo "[EESSI/2023.02]" >> cfg/repos.cfg + ./eessi_container.sh --verbose --list-repos | tee ${outfile} + grep "EESSI-pilot" ${outfile} + + export EESSI_REPOS_CFG_DIR_OVERRIDE=${PWD}/cfg + ./eessi_container.sh --verbose --list-repos | tee ${outfile2} + grep "[EESSI/2023.02]" ${outfile2} + # test use of --mode run elif [[ ${{matrix.SCRIPT_TEST}} == 'run' ]]; then outfile=out_run.txt diff --git a/eessi_container.sh b/eessi_container.sh index cdd2c017fb..76a4d34143 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -325,7 +325,7 @@ if [[ ${CONTAINER} == ${CONTAINER_URL_FMT} ]]; then CONTAINER="${PWD}/${CONTAINER_IMG}" fi fi -[[ ${INFO} -eq 1 ]] && echo "CONTAINER='${CONTAINER}'" +[[ ${VERBOSE} -eq 1 ]] && echo "CONTAINER=${CONTAINER}" # set env vars and create directories for CernVM-FS EESSI_CVMFS_VAR_LIB=${EESSI_TMPDIR}/${CVMFS_VAR_LIB} From 764e7138b0f8dfd82c81c1647bf78d04da1aec68 Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Mon, 20 Feb 2023 10:48:38 +0100 Subject: [PATCH 19/24] fix test for --list-repos; improve output for --list-repos --- .../workflows/test_eessi_container_script.yml | 2 ++ eessi_container.sh | 17 ++++++++++------- 2 files changed, 12 insertions(+), 7 deletions(-) diff --git a/.github/workflows/test_eessi_container_script.yml b/.github/workflows/test_eessi_container_script.yml index 5a44bae155..74cfd1fb10 100644 --- a/.github/workflows/test_eessi_container_script.yml +++ b/.github/workflows/test_eessi_container_script.yml @@ -53,7 +53,9 @@ jobs: outfile2=out_listrepos_2.txt mkdir -p ${PWD}/cfg echo "[EESSI/2021.12]" > cfg/repos.cfg + echo "repo_version = 2021.12" >> cfg/repos.cfg echo "[EESSI/2023.02]" >> cfg/repos.cfg + echo "repo_version = 2023.02" >> cfg/repos.cfg ./eessi_container.sh --verbose --list-repos | tee ${outfile} grep "EESSI-pilot" ${outfile} diff --git a/eessi_container.sh b/eessi_container.sh index 76a4d34143..dec082ce04 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -186,15 +186,18 @@ done set -- "${POSITIONAL_ARGS[@]}" + if [[ ${LIST_REPOS} -eq 1 ]]; then - echo "Repositories defined in the config file '${EESSI_REPOS_CFG_FILE}':" + echo "Listing available repositories with format 'name [source]':" echo " EESSI-pilot [default]" - cfg_load ${EESSI_REPOS_CFG_FILE} - sections=$(cfg_sections) - while IFS= read -r repo_id - do - echo " ${repo_id}" - done <<< "${sections}" + if [[ -r ${EESSI_REPOS_CFG_FILE} ]]; then + cfg_load ${EESSI_REPOS_CFG_FILE} + sections=$(cfg_sections) + while IFS= read -r repo_id + do + echo " ${repo_id} [${EESSI_REPOS_CFG_FILE}]" + done <<< "${sections}" + fi exit 0 fi From 47cc1c6be44896675949567d88f5ae85a998b64f Mon Sep 17 00:00:00 2001 From: Thomas Roeblitz Date: Tue, 21 Feb 2023 21:27:56 +0100 Subject: [PATCH 20/24] implemented requested changes --- .../workflows/test_eessi_container_script.yml | 8 +-- eessi_container.sh | 59 ++++++++++++++----- 2 files changed, 48 insertions(+), 19 deletions(-) diff --git a/.github/workflows/test_eessi_container_script.yml b/.github/workflows/test_eessi_container_script.yml index 74cfd1fb10..d4a9dfd53e 100644 --- a/.github/workflows/test_eessi_container_script.yml +++ b/.github/workflows/test_eessi_container_script.yml @@ -52,10 +52,10 @@ jobs: outfile=out_listrepos.txt outfile2=out_listrepos_2.txt mkdir -p ${PWD}/cfg - echo "[EESSI/2021.12]" > cfg/repos.cfg - echo "repo_version = 2021.12" >> cfg/repos.cfg - echo "[EESSI/2023.02]" >> cfg/repos.cfg - echo "repo_version = 2023.02" >> cfg/repos.cfg + echo "[EESSI/20AB.CD]" > cfg/repos.cfg + echo "repo_version = 20AB.CD" >> cfg/repos.cfg + echo "[EESSI/20HT.TP]" >> cfg/repos.cfg + echo "repo_version = 20HT.TP" >> cfg/repos.cfg ./eessi_container.sh --verbose --list-repos | tee ${outfile} grep "EESSI-pilot" ${outfile} diff --git a/eessi_container.sh b/eessi_container.sh index dec082ce04..86a510d56e 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -54,12 +54,11 @@ CVMFS_VAR_RUN="var-run-cvmfs" # directory for tmp used inside container export TMP_IN_CONTAINER=/tmp -# repository cfg file, default name (default location: $PWD) -# can be overwritten by setting env var EESSI_REPOS_CFG_DIR_OVERRIDE -export EESSI_REPOS_CFG_FILE="${EESSI_REPOS_CFG_DIR_OVERRIDE:=${PWD}}/repos.cfg" -# other repository cfg files in directory, default location: $PWD -# can be overwritten by setting env var EESSI_REPOS_CFG_DIR_OVERRIDE +# repository cfg directory and file +# directory: default $PWD or EESSI_REPOS_CFG_DIR_OVERRIDE if set +# file: directory + '/repos.cfg' export EESSI_REPOS_CFG_DIR="${EESSI_REPOS_CFG_DIR_OVERRIDE:=${PWD}}" +export EESSI_REPOS_CFG_FILE="${EESSI_REPOS_CFG_DIR}/repos.cfg" # 0. parse args @@ -288,7 +287,6 @@ else EESSI_HOST_STORAGE=$(mktemp -d --tmpdir eessi.XXXXXXXXXX) echo "Using ${EESSI_HOST_STORAGE} as tmp storage (add '--resume ${EESSI_HOST_STORAGE}' to resume where this session ended)." fi -echo "RESUME_FROM_DIR ${EESSI_HOST_STORAGE}" # if ${RESUME} is a file (assume a tgz), unpack it into ${EESSI_HOST_STORAGE} if [[ ! -z ${RESUME} && -f ${RESUME} ]]; then @@ -312,21 +310,52 @@ EESSI_TMPDIR=${EESSI_HOST_STORAGE} mkdir -p ${EESSI_TMPDIR} [[ ${VERBOSE} -eq 1 ]] && echo "EESSI_TMPDIR=${EESSI_TMPDIR}" -# configure Singularity +# configure Singularity: if SINGULARITY_CACHEDIR is already defined, use that +# a global SINGULARITY_CACHEDIR would ensure that we don't consume +# storage space again and again for the container & also speed-up +# launch times across different sessions if [[ -z ${SINGULARITY_CACHEDIR} ]]; then export SINGULARITY_CACHEDIR=${EESSI_TMPDIR}/singularity_cache mkdir -p ${SINGULARITY_CACHEDIR} fi [[ ${VERBOSE} -eq 1 ]] && echo "SINGULARITY_CACHEDIR=${SINGULARITY_CACHEDIR}" -# pull & convert image and reset CONTAINER +# we try our best to make sure that we retain access to the container image in +# a subsequent session ("best effort" only because pulling or copying operations +# can fail ... in those cases the script may still succeed, but it is not +# guaranteed that we have access to the same container when resuming later on) +# - if CONTAINER references an image in a registry, pull & convert image +# and store it in ${EESSI_TMPDIR} +# + however, only pull image if there is no matching image in ${EESSI_TMPDIR} yet +# - if CONTAINER references an image file, copy it to ${EESSI_TMPDIR} +# + however, only copy it if its base name does not yet exist in ${EESSI_TMPDIR} +# - if the image file created (pulled or copied) or resumed exists in +# ${EESSI_TMPDIR}, let CONTAINER point to it +# + thus subsequent singularity commands in this script would just use the +# image file in EESSI_TMPDIR or the originally given source (some URL or +# path to an image file) +CONTAINER_IMG= CONTAINER_URL_FMT=".*://(.*)" -if [[ ${CONTAINER} == ${CONTAINER_URL_FMT} ]]; then +if [[ ${CONTAINER} =~ ${CONTAINER_URL_FMT} ]]; then + # replace : and - with _ in match (everything after ://) and append .sif CONTAINER_IMG=${BASH_REMATCH[1]//[:-]/_}.sif - singularity pull ${CONTAINER_IMG} ${CONTAINER} - if [[ -x ${CONTAINER_IMG} ]]; then - CONTAINER="${PWD}/${CONTAINER_IMG}" + # pull container to ${EESSI_TMPDIR} if it is not there yet (i.e. when + # resuming from a previous session) + if [[ ! -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then + singularity pull ${EESSI_TMPDIR}/${CONTAINER_IMG} ${CONTAINER} fi +else + # determine file name as basename of CONTAINER + CONTAINER_IMG=$(basename ${CONTAINER}) + # copy image file to ${EESSI_TMPDIR} if it is not there yet (i.e. when + # resuming from a previous session) + if [[ ! -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then + cp -a ${CONTAINER} ${EESSI_TMPDIR}/. + fi +fi +# let CONTAINER point to the pulled, copied or resumed image file +if [[ -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then + CONTAINER="${EESSI_TMPDIR}/${CONTAINER_IMG}" fi [[ ${VERBOSE} -eq 1 ]] && echo "CONTAINER=${CONTAINER}" @@ -373,7 +402,7 @@ else cfg_load ${EESSI_REPOS_CFG_FILE} # copy repos.cfg to job directory --> makes it easier to inspect the job - cp ${EESSI_REPOS_CFG_FILE} ${EESSI_TMPDIR}/repos_cfg/. + cp -a ${EESSI_REPOS_CFG_FILE} ${EESSI_TMPDIR}/repos_cfg/. # cfg file should include: repo_name, repo_version, config_bundle, # map { local_filepath -> container_filepath } @@ -453,7 +482,8 @@ if [[ ! -z ${http_proxy} ]]; then [[ ${VERBOSE} -eq 1 ]] && echo "HTTP_PROXY_IPV4='${HTTP_PROXY_IPV4}'" echo "CVMFS_HTTP_PROXY=\"${http_proxy}|http://${HTTP_PROXY_IPV4}:${PROXY_PORT}\"" \ >> ${EESSI_TMPDIR}/repos_cfg/default.local - cat ${EESSI_TMPDIR}/repos_cfg/default.local + [[ ${VERBOSE} -eq 1 ]] && echo "contents of default.local" + [[ ${VERBOSE} -eq 1 ]] && cat ${EESSI_TMPDIR}/repos_cfg/default.local # if default.local is not BIND mounted into container, add it to BIND_PATHS if [[ ! ${BIND_PATHS} =~ "${EESSI_TMPDIR}/repos_cfg/default.local:/etc/cvmfs/default.local" ]]; then @@ -537,7 +567,6 @@ if [[ ! -z ${SAVE} ]]; then fi tar cf ${TGZ} -C ${EESSI_TMPDIR} . echo "Saved contents of '${EESSI_TMPDIR}' to '${TGZ}' (to resume, add '--resume ${TGZ}')" - echo "RESUME_FROM_TGZ ${TGZ}" fi # TODO clean up tmp by default? only retain if another option provided (--retain-tmp) From 6974e4b80e3a59643d4eac0f229f50f8f547d430 Mon Sep 17 00:00:00 2001 From: Kenneth Hoste Date: Fri, 24 Feb 2023 13:33:54 +0100 Subject: [PATCH 21/24] add verbose messages on pulling/copying/reusing of container image --- eessi_container.sh | 22 ++++++++++++++-------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 86a510d56e..01c69bdd92 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -320,6 +320,13 @@ if [[ -z ${SINGULARITY_CACHEDIR} ]]; then fi [[ ${VERBOSE} -eq 1 ]] && echo "SINGULARITY_CACHEDIR=${SINGULARITY_CACHEDIR}" +# if VERBOSE is set to 0 (no arg --verbose), add argument '-q' +if [[ ${VERBOSE} -eq 0 ]]; then + RUN_QUIET='-q' +else + RUN_QUIET='' +fi + # we try our best to make sure that we retain access to the container image in # a subsequent session ("best effort" only because pulling or copying operations # can fail ... in those cases the script may still succeed, but it is not @@ -342,7 +349,10 @@ if [[ ${CONTAINER} =~ ${CONTAINER_URL_FMT} ]]; then # pull container to ${EESSI_TMPDIR} if it is not there yet (i.e. when # resuming from a previous session) if [[ ! -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then - singularity pull ${EESSI_TMPDIR}/${CONTAINER_IMG} ${CONTAINER} + [[ ${VERBOSE} -eq 1 ]] && echo "Pulling container image from ${CONTAINER} to ${EESSI_TMPDIR}/${CONTAINER_IMG}" + singularity ${RUN_QUIET} pull ${EESSI_TMPDIR}/${CONTAINER_IMG} ${CONTAINER} + else + [[ ${VERBOSE} -eq 1 ]] && echo "Reusing existing container image ${EESSI_TMPDIR}/${CONTAINER_IMG}" fi else # determine file name as basename of CONTAINER @@ -350,7 +360,10 @@ else # copy image file to ${EESSI_TMPDIR} if it is not there yet (i.e. when # resuming from a previous session) if [[ ! -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then + [[ ${VERBOSE} -eq 1 ]] && echo "Copying container image from ${CONTAINER} to ${EESSI_TMPDIR}/${CONTAINER_IMG}" cp -a ${CONTAINER} ${EESSI_TMPDIR}/. + else + [[ ${VERBOSE} -eq 1 ]] && echo "Reusing existing container image ${EESSI_TMPDIR}/${CONTAINER_IMG}" fi fi # let CONTAINER point to the pulled, copied or resumed image file @@ -538,13 +551,6 @@ if [ ! -z ${EESSI_SOFTWARE_SUBDIR_OVERRIDE} ]; then export APPTAINERENV_EESSI_SOFTWARE_SUBDIR_OVERRIDE=${EESSI_SOFTWARE_SUBDIR_OVERRIDE} fi -# if VERBOSE is set to 0 (no arg --verbose), add argument '-q' -if [[ ${VERBOSE} -eq 0 ]]; then - RUN_QUIET='-q' -else - RUN_QUIET='' -fi - echo "Launching container with command (next line):" echo "singularity ${RUN_QUIET} ${MODE} ${EESSI_FUSE_MOUNTS[@]} ${CONTAINER} $@" singularity ${RUN_QUIET} ${MODE} "${EESSI_FUSE_MOUNTS[@]}" ${CONTAINER} "$@" From 54bdea52e86d853a923d4884c4b62682440c5b09 Mon Sep 17 00:00:00 2001 From: Kenneth Hoste Date: Fri, 24 Feb 2023 13:37:47 +0100 Subject: [PATCH 22/24] don't require --verbose for info message on pulling/copying/reusing container image --- eessi_container.sh | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index 01c69bdd92..e98cc53493 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -349,10 +349,10 @@ if [[ ${CONTAINER} =~ ${CONTAINER_URL_FMT} ]]; then # pull container to ${EESSI_TMPDIR} if it is not there yet (i.e. when # resuming from a previous session) if [[ ! -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then - [[ ${VERBOSE} -eq 1 ]] && echo "Pulling container image from ${CONTAINER} to ${EESSI_TMPDIR}/${CONTAINER_IMG}" + echo "Pulling container image from ${CONTAINER} to ${EESSI_TMPDIR}/${CONTAINER_IMG}" singularity ${RUN_QUIET} pull ${EESSI_TMPDIR}/${CONTAINER_IMG} ${CONTAINER} else - [[ ${VERBOSE} -eq 1 ]] && echo "Reusing existing container image ${EESSI_TMPDIR}/${CONTAINER_IMG}" + echo "Reusing existing container image ${EESSI_TMPDIR}/${CONTAINER_IMG}" fi else # determine file name as basename of CONTAINER @@ -360,10 +360,10 @@ else # copy image file to ${EESSI_TMPDIR} if it is not there yet (i.e. when # resuming from a previous session) if [[ ! -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then - [[ ${VERBOSE} -eq 1 ]] && echo "Copying container image from ${CONTAINER} to ${EESSI_TMPDIR}/${CONTAINER_IMG}" + echo "Copying container image from ${CONTAINER} to ${EESSI_TMPDIR}/${CONTAINER_IMG}" cp -a ${CONTAINER} ${EESSI_TMPDIR}/. else - [[ ${VERBOSE} -eq 1 ]] && echo "Reusing existing container image ${EESSI_TMPDIR}/${CONTAINER_IMG}" + echo "Reusing existing container image ${EESSI_TMPDIR}/${CONTAINER_IMG}" fi fi # let CONTAINER point to the pulled, copied or resumed image file From a4cea9afb12242340360c9ad922e13c8492c9d57 Mon Sep 17 00:00:00 2001 From: Kenneth Hoste Date: Fri, 24 Feb 2023 13:53:06 +0100 Subject: [PATCH 23/24] add check to make sure that container image exists in tmpdir --- .github/workflows/test_eessi_container_script.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/test_eessi_container_script.yml b/.github/workflows/test_eessi_container_script.yml index d4a9dfd53e..929fb22cec 100644 --- a/.github/workflows/test_eessi_container_script.yml +++ b/.github/workflows/test_eessi_container_script.yml @@ -108,6 +108,9 @@ jobs: tmpdir=$(grep "\-\-resume" ${outfile} | sed "s/.*--resume \([^']*\).*/\1/g") rm -f ${outfile} + # make sure that container image exists + test -f ${tmpdir}/ghcr.io_eessi_build_node_debian11.sif || (echo "Container image not found in ${tmpdir}" >&2 && ls ${tmpdir} && exit 1) + ./eessi_container.sh --verbose --resume ${tmpdir} --mode shell <<< "${test_cmd}" > ${outfile} cat ${outfile} grep "Resuming from previous run using temporary storage at ${tmpdir}" ${outfile} From c9758326512d824ae11e790f836c4db36dc3c527 Mon Sep 17 00:00:00 2001 From: Kenneth Hoste Date: Fri, 24 Feb 2023 15:46:52 +0100 Subject: [PATCH 24/24] fix determining filename from container URL --- eessi_container.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/eessi_container.sh b/eessi_container.sh index e98cc53493..1d76360735 100755 --- a/eessi_container.sh +++ b/eessi_container.sh @@ -344,8 +344,8 @@ fi CONTAINER_IMG= CONTAINER_URL_FMT=".*://(.*)" if [[ ${CONTAINER} =~ ${CONTAINER_URL_FMT} ]]; then - # replace : and - with _ in match (everything after ://) and append .sif - CONTAINER_IMG=${BASH_REMATCH[1]//[:-]/_}.sif + # replace ':', '-', '/' with '_' in match (everything after ://) and append .sif + CONTAINER_IMG="$(echo ${BASH_REMATCH[1]} | sed 's/[:\/-]/_/g').sif" # pull container to ${EESSI_TMPDIR} if it is not there yet (i.e. when # resuming from a previous session) if [[ ! -x ${EESSI_TMPDIR}/${CONTAINER_IMG} ]]; then