Retry the module build, count the bundles, and stop bundling the loader

The later bump worked - the build reached staging. Three new problems:

- renv restores concurrently and not always in dependency order: forecast
  was lazy-loaded while vctrs was still compiling ('there is no package
  called vctrs', six lines before 'vctrs 0.7.3 built from source in 52s').
  That aborts the whole sapply() loop, so one race cost 20 modules. Retry
  the pass up to three times; renv skips what is installed, so each pass
  converges.

- The guard only required a non-empty Modules/local, so a build with 2 of
  22 modules passed it and went on to stage and package. It now requires
  the full expected count and lists what it did get.

- bundle-libs.sh crashed on the dynamic loader: ldd prints it as
  '/lib64/ld-linux-x86-64.so.2 => ...', so the first column is a path and
  the ld-linux* denylist entry never matched. Basename the soname before
  the check.
This commit is contained in:
agw
2026-09-02 20:45:00 +02:00
parent 0680e9cb0a
commit e009dc82d3
2 changed files with 28 additions and 4 deletions
+23 -4
View File
@@ -251,7 +251,23 @@ for lock in root.glob("*/renv.lock"):
print(f"patched {patched} lockfiles")
PY
Rscript buildAllDefaultJaspModules.R
# renv restores packages concurrently and its ordering is not always
# dependency-correct: a module can be lazy-loaded while a package it needs is
# still being built, e.g. "forecast" failing with "there is no package called
# 'vctrs'" six log lines before vctrs finishes compiling. That aborts the whole
# sapply() loop, so a single race costs every remaining module.
#
# Retrying is the cheap fix: renv skips what is already installed, so each pass
# starts from more complete state and converges. Passes are capped so a genuine
# failure cannot loop forever.
EXPECTED_MODULES=22
for attempt in 1 2 3; do
log "module build pass ${attempt}/3"
Rscript buildAllDefaultJaspModules.R || true
built="$(find "$MODULE_BUNDLES" -mindepth 1 -maxdepth 1 2>/dev/null | wc -l)"
log "pass ${attempt} finished: ${built}/${EXPECTED_MODULES} bundles"
[[ "$built" -ge "$EXPECTED_MODULES" ]] && break
done
if [[ ! -d "$MODULE_LIBRARY/jaspModuleTools" ]]; then
echo "error: jaspModuleTools was not installed — install_github failed" >&2
@@ -260,11 +276,14 @@ if [[ ! -d "$MODULE_LIBRARY/jaspModuleTools" ]]; then
exit 1
fi
# Guard on the expected count, not merely "non-empty". An earlier run shipped a
# package containing 2 of 22 modules because a non-empty check passed.
bundle_count="$(find "$MODULE_BUNDLES" -mindepth 1 -maxdepth 1 2>/dev/null | wc -l)"
if [[ "$bundle_count" -eq 0 ]]; then
echo "error: the module build produced no bundles in ${MODULE_BUNDLES}" >&2
if [[ "$bundle_count" -lt "$EXPECTED_MODULES" ]]; then
echo "error: only ${bundle_count}/${EXPECTED_MODULES} module bundles were built" >&2
echo " system2() in buildAllDefaultJaspModules.R hides the real error;" >&2
echo " re-run buildModuleBundlesLocally.R by hand to see it" >&2
echo " search the log above for 'failed to install'" >&2
find "$MODULE_BUNDLES" -mindepth 1 -maxdepth 1 -printf ' have: %f\n' 2>/dev/null >&2
exit 1
fi
log "module build produced ${bundle_count} bundles"
+5
View File
@@ -73,6 +73,11 @@ while [[ "$copied_any" -eq 1 ]]; do
# userland we want to capture.
while read -r soname path; do
[[ -n "$path" && -f "$path" ]] || continue
# ldd reports some entries with an absolute path in the first column —
# the dynamic loader shows up as "/lib64/ld-linux-x86-64.so.2 => ...".
# Without this the denylist misses it and the copy below tries to create
# $LIBDIR/lib64/ld-linux-x86-64.so.2 in a directory that does not exist.
soname="${soname##*/}"
is_system_lib "$soname" && continue
[[ -f "$LIBDIR/$soname" ]] && continue
# Never bundle something that already lives inside our own tree.