auto: session-start commit — 4 file(s) at 2026-07-13 15:49:56

This commit is contained in:
librelad 2026-07-13 15:49:56 +01:00
parent cc60794367
commit e85fba3b09
4 changed files with 1035 additions and 989 deletions

File diff suppressed because it is too large Load Diff

View File

@ -275,6 +275,15 @@ fi
done < <(printf '%s\n' "${eager_files[@]}" | sort -u)
printf ')\n\n'
printf '# Shared autoload helper. A stub routes its source through this so a\n'
printf '# TRANSIENTLY-absent target file (the scripts tree is wiped then\n'
printf '# repopulated mid-deploy — see update.sh) is waited for briefly rather\n'
printf '# than failing outright. Bounded (~5s) and only while the file is\n'
printf '# unreadable, so a genuinely-missing file still fails fast. Defined in\n'
printf '# this sourced manifest so it stays in memory even while on-disk files\n'
printf '# momentarily vanish.\n'
printf '__lpAutoload() { local __f="$1" __i; for ((__i=0; __i<20; __i++)); do [ -r "$__f" ] && break; sleep 0.25; done; source "$__f"; }\n\n'
printf '# Autoload stubs — one per public function. First call unsets the\n'
printf '# stub, sources the real file (which redefines the function), then\n'
printf '# re-invokes. The `unset -f` first means a failed source degrades to a\n'
@ -287,7 +296,7 @@ fi
containers) base_var='install_containers_dir' ;;
*) base_var='install_scripts_dir' ;;
esac
printf '%s() { unset -f %s; source "${%s}%s"; %s "$@"; }\n' \
printf '%s() { unset -f %s; __lpAutoload "${%s}%s"; %s "$@"; }\n' \
"$name" "$name" "$base_var" "${fn_to_file[$name]}" "$name"
done < <(printf '%s\n' "${!fn_to_file[@]}" | sort)
} > "$OUTPUT"

View File

@ -1,17 +1,42 @@
#!/bin/bash
# LibrePortal WebUI Update Lock Check
# Checks for update lock file to prevent concurrent updates
# Guards against concurrent WebUI data refreshes.
#
# Echoes its verdict ("true" = a live lock is held, skip; "false" = clear to
# proceed) on stdout, and auto-clears a STALE lock. Callers must capture the
# echo — `result=$(webuiCheckUpdateLock)` runs the function in a subshell, so a
# global it set would never reach the caller (that was a real bug: the guard
# read an always-empty global and so never actually blocked anything).
#
# Staleness matters because the lock's remover (webuiRemoveUpdateLock) is itself
# a lazy-loaded function whose backing file can be transiently missing while the
# scripts tree is wiped+repopulated mid-deploy. If that removal is skipped once,
# the leftover lock would otherwise wedge EVERY future refresh. No single refresh
# runs anywhere near this long, so a lock older than the threshold is a leftover.
webuiCheckUpdateLock() {
local lock_file="$containers_dir/libreportal/frontend/data/updater.lock"
local stale_after=900 # seconds (15 min); far longer than any real refresh
lock_file_found=""
if [ -f "$lock_file" ]; then
isNotice "Update lock file exists: $lock_file"
lock_file_found="true"
else
isNotice "No update lock file found"
lock_file_found="false"
if [ ! -f "$lock_file" ]; then
isNotice "No update lock file found" >&2
echo "false"
return 0
fi
local now lock_mtime age
now=$(date +%s 2>/dev/null || echo 0)
lock_mtime=$(stat -c '%Y' "$lock_file" 2>/dev/null || echo 0)
age=$(( now - lock_mtime ))
if (( now > 0 && lock_mtime > 0 && age >= stale_after )); then
isNotice "Stale update lock (${age}s old ≥ ${stale_after}s) — clearing and continuing." >&2
runFileOp rm -f "$lock_file" >/dev/null 2>&1
echo "false"
return 0
fi
isNotice "Update lock file exists: $lock_file" >&2
echo "true"
return 0
}

View File

@ -26,8 +26,11 @@ webuiLibrePortalUpdate() {
if [ "$status" == "installed" ]; then
isHeader "LibrePortal WebUI Updater"
# Check for update lock file first
local result; result=$(webuiCheckUpdateLock)
# Check for update lock file first. webuiCheckUpdateLock echoes its
# verdict on stdout (and auto-clears a stale lock); capture it directly.
# A $(...) subshell means any global the function sets never reaches us
# here, so the verdict MUST come back via the echo, not a shared var.
local lock_file_found; lock_file_found=$(webuiCheckUpdateLock)
checkSuccess "Checked for update lock file."
if [[ "$lock_file_found" == "true" ]]; then